有一个带有int字段的表 - field_1 我想插入一个新行 field_1值将是所有条目的最大值加1 我试过了:
INSERT INTO table (field names, `field_1`)
VALUES (values, '(SELECT MAX(field_1) FROM table)');
我在field_1中得到'0' 我知道我可以在单独的查询中完成它。 有没有办法用一个查询执行此操作?我的意思是来自php的一个电话。
我有一个自动增量字段'id',我想添加'position'字段。我希望能够对位置进行更改,但新项目始终具有最高位置
答案 0 :(得分:7)
无论你想做什么,它都行不通,因为它不能保证是原子的。因此,并行执行此查询的两个实例可以保证在某个随机时间点相互混乱,从而导致跳过的数字和重复的数字。
数据库提供自动增量的原因正是通过保证生成这些递增值的原子性来解决这个问题。
(最后,'手动自动递增'是一个矛盾。它要么是'自动增量',要么是'手动增量'。这里只是一个自作聪明。)
编辑(在OP编辑后)
解决问题的一种低效方法是将Position
字段保留为零或NULL,然后执行UPDATE table SET Position = Id WHERE Position IS NULL
。 (假设Id
是表格中的自动编号字段。)
一种有效但繁琐的方法是在未修改Position
字段时将其保留为NULL,并仅在您决定修改它时为其赋予值。然后,每次要读取Position
字段时,请使用CASE
语句:如果Position
字段为NULL,则使用Id
的值;否则,请使用Position
。
EDIT2 (在评论中考虑OP的解释后)
如果您只有30行,我不明白为什么您甚至试图在数据库上保持订单正确。只需加载数组中的所有行,以编程方式将增量值分配给任何发现为NULL的Position
字段,当数组中行的顺序发生更改时,只需修复Position
值并更新数据库中的所有30行。
答案 1 :(得分:2)
试试这个:
INSERT INTO table (some_random_field, field_to_increment)
SELECT 'some_random_value', IF(MAX(field_to_increment) IS NULL, 1, MAX(field_to_increment) + 1)
FROM table;
或者这个:
INSERT `table`
SET
some_random_field = 'some_random_value',
field_to_increment = (SELECT IF(MAX(field_to_increment) IS NULL, 1, MAX(field_to_increment) + 1) FROM table t);
P.S。我知道它已经晚了4年但我正在寻找同样的答案。 :)
答案 2 :(得分:0)
ALTER TABLE table_name AUTO_INCREMENT = 1允许数据库将AUTO_INCREMENT重置为:
MAX(auto_increment_column)+1
它不会将其重置为1.
这可以防止任何AUTO_INCREMENT值的重复。此外,自从 AUTO_INCREMENT值是主要/唯一,重复会 反正永远不会发生执行此操作的方法是有原因的。 它不会改变任何数据库记录;只是内部计数器所以 它指向可用的最大值。如前所述 有人,不要试图超越数据库...只是让它来处理它。 它可以很好地处理AUTO_INCREMENT的重置。 See gotphp