dict
を使用してSQL INSERT
を実行しようとしています。ロジックは基本的に次のようになります。
INSERT INTO table (dict.keys()) VALUES dict.values()
しかし、これを行うための正しい構文/フローを理解するのは大変です。これは私が現在持っているものです:
# data = {...}
sorted_column_headers_list = []
sorted_column_values_list = []
for k, v in data.items():
sorted_column_headers_list.append(k)
sorted_column_values_list.append(v)
sorted_column_headers_string = ', '.join(sorted_column_headers_list)
sorted_column_values_string = ', '.join(sorted_column_values_list)
cursor.execute("""INSERT INTO title (%s)
VALUES (%s)""",
(sorted_column_headers_string, sorted_column_values_string))
これから、SQL例外を取得します(コンマが自分の持っている値の一部に含まれているという事実に関連すると思います)。上記を行う正しい方法は何ですか?
クエリにパラメータープレースホルダーを追加します。これにより、必要なものが得られる場合があります。
qmarks = ', '.join('?' * len(myDict))
qry = "Insert Into Table (%s) Values (%s)" % (qmarks, qmarks)
cursor.execute(qry, myDict.keys() + myDict.values())
これをMySQLで使用することについてのコメントは完全ではないと思います。 MySQLdbは列内のパラメーター置換を行わず、値(IIUC)のみを実行します。
placeholders = ', '.join(['%s'] * len(myDict))
columns = ', '.join(myDict.keys())
sql = "INSERT INTO %s ( %s ) VALUES ( %s )" % (table, columns, placeholders)
cursor.execute(sql, myDict.values())
ただし、列でエスケープされていないため、最初に列を確認することをお勧めします。
より完全なソリューションについては、 http://mail.python.org/pipermail/tutor/2010-December/080701.html を参照してください
ここでは常に良い答えですが、Python 3では、次のように書く必要があります。
_placeholder = ", ".join(["%s"] * len(dict))
stmt = "insert into `{table}` ({columns}) values ({values});".format(table=table_name, columns=",".join(dict.keys()), values=placeholder)
cur.execute(stmt, list(dict.values()))
_
dict.values()
をリストに変換することを忘れないでください。Python 3、dict.values()
はリストではなくビューを返します。
また、[〜#〜] not [〜#〜]stmt
にdict.values()
を注ぎます。これは、文字列からjoin
ingを挿入すると、挿入時にMySQLエラーが発生しました。そのため、常にcur.execute()
に動的に配置する必要があります。
@furicleの解決策を試しましたが、それでもすべてを文字列として入力します-あなたの辞書が混在している場合、これはあなたが望むように機能しないかもしれません。私は同様の問題を抱えていましたが、これが私が思いついたものです-これはクエリビルダにすぎず、あなたはそれを(変更して)選択して任意のデータベースで動作することができます。ご覧ください!
def ins_query_maker(tablename, rowdict):
keys = Tuple(rowdict)
dictsize = len(rowdict)
sql = ''
for i in range(dictsize) :
if(type(rowdict[keys[i]]).__== 'str'):
sql += '\'' + str(rowdict[keys[i]]) + '\''
else:
sql += str(rowdict[keys[i]])
if(i< dictsize-1):
sql += ', '
query = "insert into " + str(tablename) + " " + str(keys) + " values (" + sql + ")"
print(query) # for demo purposes we do this
return(query) #in real code we do this
これは粗雑であり、依然として健全性チェックなどが必要ですが、意図したとおりに機能します。口述のために:
tab = {'idnumber': 1, 'fname': 'some', 'lname': 'dude', 'dob': '15/08/1947', 'mobile': 5550000914, 'age' : 70.4}
クエリを実行すると、次の出力が得られます
table='mytable'
columns_string= '('+','.join(myDict.keys())+')'
values_string = '('+','.join(map(str,myDict.values()))+')'
sql = """INSERT INTO %s %s
VALUES %s"""%(table, columns_string,values_string)
私はこのスレッドを使用するために使用し、ずっとシンプルに保つようにしました
_ins_qry = "INSERT INTO {tablename} ({columns}) VALUES {values};" .format(
tablename=my_tablename,
columns=', '.join(myDict.keys()),
values=Tuple(myDict.values())
)
cursor.execute(ins_qry)
_
挿入された行の主キーが必要な場合は、db_connection.commit()
を使用して挿入されたデータをコミットし、_cursor.lastrowid
_を使用してください。