Sqlite primary key on multiple columns
在sqlite中指定一个以上列的主键的语法是什么?
根据文件,它是
1 2 3 4 5 6 | CREATE TABLE something ( column1, column2, column3, PRIMARY KEY (column1, column2) ); |
1 2 3 4 5 6 | CREATE TABLE something ( column1 INTEGER NOT NULL, column2 INTEGER NOT NULL, value, PRIMARY KEY ( column1, column2) ); |
对。但请记住,这样的主键允许两列中的
创建表,如下所示:
1 2 | sqlite> CREATE TABLE something ( column1, column2, value, PRIMARY KEY (column1, column2)); |
现在这项工作没有任何警告:
1 2 3 4 5 | sqlite> insert into something (value) VALUES ('bla-bla'); sqlite> insert into something (value) VALUES ('bla-bla'); sqlite> select * from something; NULL|NULL|bla-bla NULL|NULL|bla-bla |
基本的:
1 2 3 4 5 | CREATE TABLE table1 ( columnA INTEGER NOT NULL, columnB INTEGER NOT NULL, PRIMARY KEY (columnA, columnB) ); |
如果列是其他表的外键(常见情况):
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | CREATE TABLE table1 ( table2_id INTEGER NOT NULL, table3_id INTEGER NOT NULL, FOREIGN KEY (table2_id) REFERENCES table2(id), FOREIGN KEY (table3_id) REFERENCES table3(id), PRIMARY KEY (table2_id, table3_id) ); CREATE TABLE table2 ( id INTEGER NOT NULL, PRIMARY KEY id ); CREATE TABLE table3 ( id INTEGER NOT NULL, PRIMARY KEY id ); |
主键字段应声明为非空(这是非标准的定义主键的作用是它必须是唯一的,不能为空)。但下面是一个很好的实践任何DBMS中的所有多列主键。
1 2 3 4 5 6 7 8 | create table foo ( fooint integer not null ,foobar string not null ,fooval real ,primary key (fooint, foobar) ) ; |
自从3.8.2版的sqlite以来,显式非空规范的另一种选择是"without rowid"规范:[1]
1 2 | NOT NULL is enforced on every column of the PRIMARY KEY in a WITHOUT ROWID table. |
"without rowid"表具有潜在的效率优势,因此需要考虑的一个不那么冗长的替代方法是:
1 2 3 4 5 6 | CREATE TABLE t ( c1, c2, c3, PRIMARY KEY (c1, c2) ) WITHOUT ROWID; |
例如,在sqlite3提示下:
sqlite> insert into t values(1,null,3);
Error: NOT NULL constraint failed: t.c2
在另一种方式中,您还可以使两列主键
下面的代码在sqlite中创建一个以2列作为主键的表。
解决方案:
1 | CREATE TABLE IF NOT EXISTS users (id TEXT NOT NULL, name TEXT NOT NULL, pet_name TEXT, PRIMARY KEY (id, name)) |