在SQLite中一次插入一行值

时间:2016-03-26 00:06:37

标签: python database sqlite

对于下面代码中的每个循环,INSERT INTO将指定的值插入到新行中的正确列BUT中:

import sqlite3

conn = sqlite3.connect('testtable.sqlite3')
cur = conn.cursor()
cur.executescript(''' DROP TABLE IF EXISTS Tracks;
                      CREATE TABLE Tracks (id, singer, song)''')

lst = ['id', 'singer', 'song']

for i in range(len(lst)):
    print 'Enter a value for column', lst[i]
    insdata = raw_input('>>> ')
    cur.execute('''INSERT INTO Tracks ({col}) VALUES (?)'''\
    .format(col=lst[i]), (insdata, ))
conn.commit()
conn.close()

问题:我怎样才能告诉SQLite 不要更改每个循环中的行并一次填充一行表?

注意:我不想在我的代码中明确引用所有列名称(例如,INSERT INTO表(所有列)),因为在我的练习脚本中我让用户输入他们的姓名和总人数。

2 个答案:

答案 0 :(得分:1)

不要在循环中修改数据库。相反,使用循环来填充数据结构(列表,字典...)以及您想要在新行中的所有内容。然后,在循环之后,使用该数据结构来构建包含所有数据的INSERT...子句。

如果不清楚:在没有创建新行的情况下,您无法告诉SQLite INSERT ...INSERT始终会创建一个新行。

答案 1 :(得分:1)

希望这是可行的。我回复自己以供将来参考并保留上面的初始代码,以供比较。我评论我做了什么以及如何在代码中找到问题的答案。感到悲伤的是因为被描述了一个实际上可以通过以下技巧解决的问题而被低估了...

import sqlite3

conn = sqlite3.connect('testdb.sqlite3')
cur = conn.cursor()

lst = ['id', 'singer', 'song'] # let's assume that through prompts, user has 
                               # previously added these values and the
                               # script put them in this list.

cur.executescript('''DROP TABLE IF EXISTS Tracks;
                     CREATE TABLE Tracks (id, singer, song)''')
conn.commit()

def populate_tb():
    print 'Insert  value for column: ', lst[0] 
    inp = raw_input('>>> ') # user types the value for the first column (in 
                            # this example, id column)
    cur.execute('INSERT INTO Tracks ({col}) VALUES (?)'\
.format(col=lst[0]), (inp,))
                       # the value is inserted to id column.
    conn.commit()
    if len(lst)-1 > 1: # meaning, continue iff user created a table with 
                       # more than one column. I subtract one because lst[0] 
                       # item has already been assigned a value above with 
                       # the INSERT.
        for i in range(len(lst)-1): # I run a loop for the remaining list 
                                    # items (singer, song columns)
            print 'Insert value for column: ', lst[i+1]
            inps = raw_input('>>> ')
            cur.execute('UPDATE Tracks SET {col} = (?) WHERE id = (?)'\
.format(col=lst[i+1]), (inps,inp))
            # And here is the solution. I just UPDATE the newly created row so 
            # I get what I want: user is prompted to populate a table, 'cell 
            # by cell', horizontally, without changing line as it was 
            # happening with my initial code in the top. Instead of 
            # declaring explicitly which columns to populate (which is 
            # impossible in my scenario since the user is prompted 
            # dynamically to create the columns), I use only one column 
            # reference which varies according to the loop counter that 
            # traverses list's items.
            conn.commit()

populate_tb() 

所以我最初的问题(根据我们的上下文):如何告诉SQLite不要在每个循环中更改行并一次填充一行表?已回答您可以告诉' SQLite,您只是插入第一个值,然后更新此行中的其余空单元格。