2010-01-18 50 views
4

我有一个带有单个主键(称为pkey)的自动递增的Mysql表,我想克隆一行,保持所有数据相同,除了主键成为由自动增量定义的下一个可用值。有主键的Mysql克隆行

我的第一个问题是,下列查询可能吗?

UPDATE `table` SET pkey='next_available_primary_key' WHERE pkey='old_primary_key' 

如果试图

UPDATE `table` SET pkey=null WHERE pkey='old_primary_key' 

但只设置主键到零值。提前感谢任何帮助/建议。

UPDATE:

我想我应该补充一点,我真的不希望在表中的数据的两个副本。我只是想改变主键。所以,如果我是使用INSERT SELECT我将不得不使用对重复密钥更新PKEY补偿=“next_available_primary_key”我只是不知道如何做到这一点...

+0

出于好奇:什么是你的目标?因为您可能会滥用主键来实现某些目标(如订购数据),而不是其目的。 – 2010-01-18 04:09:57

回答

3
insert into t select 0,a,b,c,d,e from t where id = some_id 

使用0作为AUTO_INCREMENT值列,MySQL将使用编辑为您的新评论的一个可用...

,如果你想在ID更改为下一个可用的一个,

update tbl set id = (select auto_increment from 
    information_schema.tables where table_name = 'tbl') where id = 4; 
7

你想INSERT,不更新,如果你正试图在表格中创建一个新行。

这个怎么样?确保您的PKEY设置为自动增量。

INSERT INTO `table` (col,col,col) /*name all the columns EXCEPT the primary key*/ 
SELECT col,col,col /*name all the columns EXCEPT the primary key*/ 
    FROM 'table` 
WHERE pkey='old_primary_key' 
+0

所以我想到了这一点,我可能会使用这种解决方案,但我希望有一个更清洁的解决方案,我不需要列出除主键以外的所有字段。 – 2010-01-18 01:55:16

+2

我做了很多这种东西,我使用元数据(information_schema.COLUMNS)来构建我的查询。列。如果该列是表的主键的一部分,则COLUMN_KEY ='PRI',如果不是,则为空字符串。 – 2010-01-22 11:34:39

+0

无论如何,你将不得不使用一些脚本来建立查询。 我认为你将不得不使用临时表,这取决于你的数据库引擎。 – 2011-05-26 10:20:36

2

如何解决在clone-sql-record上找到的解决方案?

CREATE TEMPORARY TABLE %1 ENGINE=MEMORY SELECT * FROM mytable WHERE myid=%2; 

UPDATE %1 SET myid=%3; 

INSERT INTO mytable SELECT * FROM %1; 

DROP TABLE %1; 

其中

  • %1是 “T” + raw_time_stamp,前T20120124132754
  • %2 OLDID
  • %3是NEWID
  • 表的
0

克隆记录with autoincremented primary key

CREATE TEMPORARY TABLE `tmp` SELECT * FROM `your_table_name`; 

UPDATE `tmp` SET id = NULL ; 

INSERT INTO `your_table_name` SELECT * FROM `tmp`; 

DROP TEMPORARY TABLE IF EXISTS `tmp`; 
0

请注意,其他解决方案似乎适用于允许主键列为空的源表。由于这是不是这样的我,我遇到了一个错误 - 它可以通过改变临时表很容易解决(我预计id是主键):

CREATE TEMPORARY TABLE tmp_clone ENGINE=MEMORY 
    SELECT * FROM my_source_table WHERE id=some_id; 

ALTER TABLE tmp_clone MODIFY id bigint(20) default null; 
UPDATE tmp_clone SET id=null; 

INSERT INTO my_source_table SELECT * FROM tmp_clone; 

DROP TABLE tmp_clone; 

SELECT * from my_source_table where id = last_insert_id();