3 回答
TA贡献1793条经验 获得超6个赞
我想不出您不应该使用参数化查询的充分理由。您已经知道 CSV 标题中的列名称(并且您可能总是知道这一点,否则您将如何创建表?),那么为什么不按照推荐的方式进行操作呢?当您这样做时,您已经打开了该文件with open...
并使用DictReader
. 尽管它不是面向公众的代码,但如果 CSV 中存在类似 SQL 注入的元素,您的数据库可能会崩溃。
DictReader
作为字典读取该行。当您迭代字典时,您得到的是它的键而不是它的值。另外,请记住,您想要将它们插入到 varchar 列中,因此您需要将它们括在'
你需要做
col_vals = ", ".join([f"'{v}'" for v in row.values()])
sql_str1=f'insert into rd.data values ({colvals})'
我强烈建议您使用如下参数来执行此操作:
col_names = ",".join(row) # 'id,first_name,last_name,email,boole,coin'
params = ",".join("%s" for x in row) # '%s,%s,%s,%s,%s,%s'
query = f'insert into rd.data ({col_names}) values ({params})'
mycursor.execute(query, row.values())
TA贡献1852条经验 获得超1个赞
因为您csv.DictReader
可以轻松地从字典键中检索列。事实上,此方法会跳过第一行。此外,请考虑executemany
仅对两个游标调用进行参数化:
with open(r"C:\Path\To\MOCK_DATA.csv") as csvfile:
csv_reader = csv.DictReader(csvfile)
data = [row for row in csv_reader]
sql1 = f'CREATE TABLE rd.data ( {" VARCHAR(50), ".join(data[0].keys())} VARCHAR(50))'
mycursor.execute(sql1)
mydb.commit()
sql2 = "INSERT INTO rd.data (`{cols}`) VALUES ({prms})"
sql2 = sql2.format(cols="`, `".join(data[0].keys()),
prms=", ".join(['%s'] * len(data[0])))
mycursor.executemany(sql2, [list(d.values()) for d in data])
mydb.commit()
Online Demo (使用 SQLite 但应与 MySQL 保持一致)
TA贡献1877条经验 获得超6个赞
我能够使用以下代码解决该问题:
mycursor.execute("drop table if exists rd.data_with_header")
#r"C:\Users\rcsid\Documents\Office Programs\Working prog\MOCK_DATA.csv"
#re.sub('[^a-zA-Z0-9]\n\.', '_', row)
reader = csv.DictReader(open(r"C:\Users\rcsid\Documents\Office Programs\Working prog\MOCK_DATA.csv",encoding='utf-8',errors='ignore'), delimiter=',')
rowHeaders = reader.fieldnames
print(rowHeaders)
for i in rowHeaders:
field_name.append(re.sub('[^A-Za-z0-9]+', '_', i))
print(field_name)
print(f'''create table rd.data_with_header ( {" varchar(100), ".join(field_name)} varchar(100))''')
sql_str=f'''create table rd.data_with_header ( {" varchar(100), ".join(field_name)} varchar(100))'''
mycursor.execute(sql_str)
for row in reader:
sql_str1=f'''insert into rd.data values ('{"',' ".join(row.values())}')'''
print(sql_str1)
mycursor.execute(sql_str1)
添加回答
举报