使用pyodbc时读取数据是ok 的,但写入时会报错
import pandas as pd
import pyodbc
conn = pyodbc.connect(
r'DRIVER={SQL Server};'
r'SERVER=10.2.3.24,1433;'
r'DATABASE=somedb;'
r'UID=username;'
r'PWD=passwd'
)
sqldata = pd.read_sql("select * from testtable",conn)
df = pd.DataFrame(sqldata)
for i in df.index:
while True:
if "**" in df.HandleCMRule[i]:
df.HandleCMRule[i] = df.HandleCMRule[i].replace("**", "*")
else:
df.HandleCMRule[i] = df.HandleCMRule[i].replace("*", ".*?")
df.HandleCMRule[i] = df.HandleCMRule[i].replace("..*??", ".*?")
break
当将DataFrame写回数据库时就报错了
df.to_sql("testtable", con=conn, index=False,if_exists="replace")
错误如下:
Traceback (most recent call last):
File "C:\ProgramData\Anaconda3\lib\site-packages\pandas\io\sql.py", line 1400, in execute
cur.execute(*args)
pyodbc.ProgrammingError: ('42S02', "[42S02] [Microsoft][ODBC SQL Server Driver][SQL Server]对象名 'sqlite_master' 无效。 (208) (SQLExecDirectW); [42S02] [Microsoft][ODBC SQL Server Driver][SQL Server]无法预定义语句。 (8180)")
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "C:\ProgramData\Anaconda3\lib\site-packages\IPython\core\interactiveshell.py", line 2963, in run_code
exec(code_obj, self.user_global_ns, self.user_ns)
File "<ipython-input-3-447cbecb2c26>", line 1, in <module>
df.to_sql("AIDiagnosisClinicalManifestationTest", con=conn, index=False)
File "C:\ProgramData\Anaconda3\lib\site-packages\pandas\core\generic.py", line 2127, in to_sql
dtype=dtype)
File "C:\ProgramData\Anaconda3\lib\site-packages\pandas\io\sql.py", line 450, in to_sql
chunksize=chunksize, dtype=dtype)
File "C:\ProgramData\Anaconda3\lib\site-packages\pandas\io\sql.py", line 1502, in to_sql
table.create()
File "C:\ProgramData\Anaconda3\lib\site-packages\pandas\io\sql.py", line 561, in create
if self.exists():
File "C:\ProgramData\Anaconda3\lib\site-packages\pandas\io\sql.py", line 549, in exists
return self.pd_sql.has_table(self.name, self.schema)
File "C:\ProgramData\Anaconda3\lib\site-packages\pandas\io\sql.py", line 1514, in has_table
return len(self.execute(query, [name, ]).fetchall()) > 0
File "C:\ProgramData\Anaconda3\lib\site-packages\pandas\io\sql.py", line 1412, in execute
raise_with_traceback(ex)
File "C:\ProgramData\Anaconda3\lib\site-packages\pandas\compat\__init__.py", line 403, in raise_with_traceback
raise exc.with_traceback(traceback)
File "C:\ProgramData\Anaconda3\lib\site-packages\pandas\io\sql.py", line 1400, in execute
cur.execute(*args)
pandas.io.sql.DatabaseError: Execution failed on sql 'SELECT name FROM sqlite_master WHERE type='table' AND name=?;': ('42S02', "[42S02] [Microsoft][ODBC SQL Server Driver][SQL Server]对象名 'sqlite_master' 无效。 (208) (SQLExecDirectW); [42S02] [Microsoft][ODBC SQL Server Driver][SQL Server]无法预定义语句。 (8180)")
折腾半天总是找到方法了。
修改后的代码如下:
import pandas as pd
from sqlalchemy import create_engine
engine = create_engine('mssql+pyodbc://username:passwd@10.2.3.24:1433/somedb?driver=SQL+Server')
#?driver=SQL+Server 没加这个会报错 找不到驱动……
sqldata = pd.read_sql("select * from testtable",engine)
df = pd.DataFrame(sqldata)
for i in df.index:
while True:
if "**" in df.HandleCMRule[i]:
df.HandleCMRule[i] = df.HandleCMRule[i].replace("**", "*")
else:
df.HandleCMRule[i] = df.HandleCMRule[i].replace("*", ".*?")
df.HandleCMRule[i] = df.HandleCMRule[i].replace("..*??", ".*?")
break
df.to_sql("testtable", con=engine, index=False, if_exists="replace", chunksize=10)
# chunksize 每次传递的数据量大小 ,如果字段较多这个值设的小一些,默认1000