MySQL交换主键值

时间:2012-09-06 14:50:49

标签: mysql

sql swap primary key values的已接听答案因错误Can't reopen table: 't'而失败 - 可能这与打开同一个表格两次写入有关,导致锁定。

是否有任何快捷方式,或者我必须同时获取两者,将其中一个设置为NULL,将第二个设置为第一个,然后将第一个设置为先前获取的第二个值?

2 个答案:

答案 0 :(得分:1)

不要使用临时表。

来自manual

  

您不能在同一查询中多次引用TEMPORARY表。   例如,以下内容不起作用:

mysql> SELECT * FROM temp_table, temp_table AS t2;
ERROR 1137: Can't reopen table: 'temp_table'
  

如果您引用临时表倍数,也会发生此错误   在不同别名下的存储函数中的次数,即使是   引用发生在函数内的不同语句中。

<强>更新

对不起,如果我说不对,但为什么简单的三方交换不起作用?

像这样:

create table yourTable(id int auto_increment, b int, primary key(id));

insert into yourTable(b) values(1), (2);
select * from yourTable;

DELIMITER $$
create procedure pkswap(IN a int, IN b int)
BEGIN
select @max_id:=max(id) + 1 from yourTable;
update yourTableset id=@max_id where id = a;
update yourTableset id=a where id = b;
update yourTableset id=b where id = @max_id;
END $$
DELIMITER ;

call pkswap(1, 2);

select * from yourTable;

答案 1 :(得分:0)

要交换1和2的id值,我会使用这样的SQL语句:

编辑:根据我的测试,这不适用于InnoDB表,只适用于MyISAM表。 <击>

<击>
UPDATE mytable a 
  JOIN mytable b ON a.id = 1 AND b.id = 2 
  JOIN mytable c ON c.id = a.id
   SET a.id = 0
     , b.id = 1
     , c.id = 2 

<击>

要使此语句起作用,表中的id值0必须不存在,任何未使用的值都是合适的......但要使其在单个SQL语句中起作用,您需要(暂时)使用第三个id值。


此解决方案适用于常规MyISAM表,而不适用于临时表。我错过了这是在临时表上执行的,我对您报告的错误消息Can't reopen table:感到困惑。

要在临时表中交换id值1和2,我再次使用临时占位符值0运行三个单独的语句:

UPDATE mytable a SET a.id = 0 WHERE a.id = 1;
UPDATE mytable b SET b.id = 1 WHERE b.id = 2;
UPDATE mytable c SET c.id = 2 WHERE c.id = 0;

编辑:修正错误