【问题标题】:cant resolve cryptic error in Python/sqlite program无法解决 Python/sqlite 程序中的神秘错误
【发布时间】:2012-03-25 17:52:15
【问题描述】:

我遇到了这个我无法解决的错误 我在 Python 中编写了一些代码,使用 tkinter 接口将数据从文本文件传输到 sqlite。

首先,相关代码如下:

def submit_data(self):
    self.new_filename = self.file_entry.get()
    self.new_tablename = self.table_entry.get()
    self.new_fieldname = self.field_entry.get().split(',')

    #print(self.new_fieldname)
    self.create_new.destroy()

    from sqlite3 import dbapi2 as sqlite

    con = sqlite.connect(self.new_filename)    
    cur = con.cursor()
    cur.execute('CREATE TABLE ' + self.new_tablename + '(id INTEGER PRIMARY KEY)')
    for field in self.new_fieldname:
        cur.execute('ALTER TABLE ' + self.new_tablename + ' ADD ' + field)

    with open(self.filename, 'r', encoding='latin-1') as self.the_file:    
        status = True
        #_keynumber=1
        while status:
            _row = self._next_line()

            if _row:
                _entry_list = _row.split(',')
                # add space after text line comma for formatting
                _entry_list = ', '.join(_entry_list)
                #print(_entry_list)

                #entries = {'row': _keynumber, 'entry': _entry_list} 
                #row_entry = "INSERT INTO " + self.new_tablename + " VALUES(" + _entry_list + ")"
                cur.execute("INSERT INTO " + self.new_tablename + " VALUES(" + _entry_list + ")")

                #_colrange = range(_colamount)                    

                #_keynumber+=1

            else:
                status = False   

        con.commit()

在 cur.execute("INSERT INTO " ... 行(大约 6 行)我收到此错误: ** cur.execute("INSERT INTO " + self.new_tablename + " VALUES(" + _entry_list + ")") sqlite3.OperationalError:靠近“。”:语法错误**

我已经用许多不同的方式改变了这一点。有一次,我将整个“INSERT INTO ... VALUES ....”字符串作为变量并使用了

cur.execute(*variable*)

当我这样做时,错误是相同的,除了“OperationalError: near "." 是 "OperationalError: near "of" ...并且任何地方都没有 'of'。

我真的很困惑和沮丧。有人帮我分解一下吗??

谢谢 F

其读取的文本文件行设置如下: 好莱坞的大明星,桑德拉·狄金森

所以我想如果我使用 .join() 在逗号后放置一个空格,那么对于 INSERT INTO 语句,字符串将相当于两个 VALUES。

【问题讨论】:

    标签: python sqlite python-3.x tkinter


    【解决方案1】:

    删除

    _entry_list = ', '.join(_entry_list)
    

    并使用

    cur.execute("INSERT INTO " + self.new_tablename + "(" + ",".join(self.new_fieldname) +") VALUES(" + ",".join(("?" for i in xrange(len(_entry_list)))) + ")", _entry_list)
    

    这将参数化您的查询并自动引用_entry_list 中的所有值。

    您仍然需要手动引用 self.new_tablenameself.new_fieldname。这应该在您在任何 sql 语句中使用它们之前。

    【讨论】:

    • 这是正确的方法。请注意,使用参数化查询还可以保护您免受 SQL 注入攻击。 (What happens if someone types "Robert'); DROP TABLE Students;" into your GUI?)
    • 谢谢,这似乎可行,但我现在遇到了一种周期性问题。因为当我创建表时,我从 id 列开始,这段代码告诉我我的表有三列,但我只提供了 2 个值。当我添加一个绑定时,例如“VALUES(?”),它说绑定太多。所以要么提供的值绑定太多,要么列太多。我修改了不同的东西,比如上面的例子和得到相同类型的错误。
    • 是的,我刚刚删除了该行。我似乎仍然无法解决太多绑定/太多列的问题。
    • 现在似乎一切正常,除了因为在 CREATE TABLE 上我默认使用 id INTEGER PRIMARY KEY 然后添加了两列。所以我得到: sqlite3.OperationalError: table mememel 有 3 列,但提供了 2 个值,如果我添加绑定,我得到: sqlite3.ProgrammingError: 提供的绑定数量不正确。当前语句使用 3,并且提供了 2。仍然给我带来核心问题。
    【解决方案2】:

    你需要引用你的字符串。

    正如所写,您的 SQL 语句是:

    INSERT INTO foo VALUES(Hello there, world, I am, unquoted, string, not good)

    你应该使用:

    INSERT INTO foo VALUES("Hello there","world","I am","quoted","string","hooray")

    【讨论】:

    • ahhh,所以文本文件字符串中的两个子字符串也需要引用?关于以编程方式执行此操作的最佳方法的任何建议?字面上有成千上万,不能用手做,大声笑
    • _entry_list = '", "'.join(_entry_list)替换_entry_list = ', '.join(_entry_list),然后通过_entry_list = '"'+_entry_list[:-1]+_entry_list[len(_entry_list)-1]+'"'处理边缘情况
    【解决方案3】:

    我建议您执行以下操作:

    a) 不执行语句,而是将其打印到控制台。换行:

    cur.execute("INSERT INTO " + self.new_tablename + ...)
    

    到:

    print "INSERT INTO " + self.new_tablename + ...
    

    b) 进行此更改后运行您的程序。查看您打印到控制台的 SQL 语句。它们是有效的 SQL 语句吗?启动 SQLite 命令行,并复制/粘贴程序生成的语句。当您尝试执行粘贴的语句时,SQLite 是否给出任何错误?

    【讨论】:

    • 是的,我已经做到了。然后又做了一次。我确实需要引用这些子字符串,我只是遇到了麻烦。我不确定如何将该列表拆分为子字符串并引用它们 - 我可以,但那将是特定于此文本文件的代码。我想这样做,所以它足够抽象,可以处理任何文本文件,无论它在列表中有 2 个还是 10 个条目。
    猜你喜欢
    • 2016-03-11
    • 2013-02-11
    • 1970-01-01
    • 1970-01-01
    • 2014-04-11
    • 1970-01-01
    • 2015-03-13
    • 1970-01-01
    • 2015-03-13
    相关资源
    最近更新 更多