我正在开发一个与简单的sqlite数据库交互的Python程序。我试图构建一个搜索工具,根据用户输入,可以交互式地过滤"过滤"数据库然后返回与搜索匹配的行(项)。例如......
我的Python程序(通过if语句,cgi.FieldStorage()和whatnot)应该能够接受用户输入然后搜索数据库。这是该计划的一般代码:
import cgitb; cgitb.enable()
import cgi
import sys
import sqlite3 as lite
import sys
con = lite.connect('bikes.db')
form = cgi.FieldStorage()
terrain_get = form.getlist("terrain")
terrains = ",".join(terrain_get)
handlebar_get = form.getlist("handlebar")
handlebars = ",".join(handlebar_get)
kickstand = form['kickstand'].value
如您所见,该部分是接收用户输入的部分;工作正常(我认为)。接下来,我需要帮助的地方:
if 'dirtrocky' not in terrains:
FILTER the database to not return items that have "dirtrocky' in their terrain field
然后在程序中,我希望能够扩展我的过滤器:
if 'drop' not in handlebars:
FILTER the database to, much like in previous one, not return items that have 'drop' in their 'handlebar' field
我的问题是,我如何过滤数据库?理想情况下,我的最终结果应该是在“我过滤掉”之后留下的行的ID元组。以上。
谢谢!
答案 0 :(得分:2)
首先,您应该定义数据库架构。最常见的方法是创建完全规范化的数据库,如:
CREATE TABLE bikes (
bike_id INTEGER AUTOINCREMENT PRIMARY KEY,
manufacturer VARCHAR(20),
price FLOAT,
...
);
CREATE TABLE terrains (
terrain_id INTEGER AUTOINCREMENT PRIMARY KEY,
terrain VARCHAR(20),
...
);
CREATE TABLE handlebars (
handlebar_id INTEGER AUTOINCREMENT PRIMARY KEY,
handlebar VARCHAR(20),
...
);
CREATE TABLE bike_terrain (
bike_id INTEGER,
terrain_id INTEGER
);
CREATE TABLE bike_handlebar (
bike_id INTEGER,
handlebar_id INTEGER
);
请注意,bikes
表中不包含任何有关地形类型或手柄的信息:此信息将存储在bike_terrain
等连接表中。
这个完全规范化的数据库使填充起来有点麻烦,但另一方面,它使查询更容易。
如何查询多值字段?
您需要动态构建SQL语句,如下所示:
SELECT
b.manufacturer,
b.price
FROM bikes b,
terrains t,
bike_terrain bt
WHERE b.bike_id = bt.bike_id
AND t.terrain_id = bt.terrain_id
AND t.terrain IN ('mountain', 'dirt', ...) -- this will be built dynamically
... -- add more for handlebars, etc...
通过动态构建SQL语句,几乎必须构建和动态添加整个WHERE子句。
我强烈建议您使用一些优秀的SQLite GUI来解决这个问题。在Windows上,SQLite Expert Personal非常棒,而且在Linux sqliteman
上很棒。
一旦你填充了数据库并且它有超过几百行的东西,你应该添加适当的索引,以便它能够快速运行。祝你好运!