Jac*_*cob 2 sql postgresql insert
有没有办法在没有专门输入ID的情况下将新记录插入到没有自动增量ID的表中.我只想要ID为lastId + 1.
INSERT INTO lists VALUES (id,'KO','SPH', '5') //新的id
不要那样做!永远!甚至不要考虑这样做!
这个错误的解决方案似乎(它没有)为你工作:
INSERT INTO lists VALUES ((SELECT max(id)+1 FROM lists),'KO','SPH', '5');
Run Code Online (Sandbox Code Playgroud)
但是,如果有人试图与你同时插入,你们两个都会得到相同的结果id,这将导致无效的结果.你真的应该使用一个sequence或更可靠的机制(当你不能在序列中有漏洞时,辅助表是常见的,但它有一些缺点[它会锁定]).您甚至可以使用serial数据类型使其更容易(它在下面创建一个序列):
CREATE TABLE lists(id serial, col2 text, col3 text, ...);
-- If you don't specify "id", it will autogenerate for you:
INSERT INTO lists(col2, col3, ...) VALUES('KO','SPH', ...);
-- You can also specify using DEFAULT (the same as above):
INSERT INTO lists(id, col2, col3, ...) VALUES(DEFAULT, 'KO','SPH', ...);
Run Code Online (Sandbox Code Playgroud)
如果你真的,真的,真的,真的,不能创建和使用序列,你可以像上面那样做,但你必须处理异常(假设id字段是PK或UK,并使用读取已提交的事务),某事像那样(在PL/pgSQL中):
DECLARE
inserted bool = false;
BEGIN
WHILE NOT inserted LOOP;
BEGIN
INSERT INTO lists
VALUES ((SELECT coalesce(max(id),0)+1 FROM lists),'KO','SPH', '5');
inserted = true;
EXCEPTION
WHEN unique_violation THEN
NULL; -- do nothing, just try again
END;
END LOOP;
END;
Run Code Online (Sandbox Code Playgroud)
但同样,我强烈建议你避免它:使用一个序列并且快乐... = D.
另外,我知道这是一个例子,但在INSERT INTO子句上使用显式列列表.