7

私はこれをやろうとしています

  • table という名前のブログのすべての行を取得します。
  • それらを一時データベースにコピーします
  • この一時テーブル レコードの言語フィールドを編集します
  • ブログテーブルに挿入

そして、私は次のように試しています:

CREATE TEMPORARY TABLE tmptable SELECT * FROM blogs WHERE lan = 2;
UPDATE tmptable SET lan = 1;
INSERT INTO blogs SELECT * FROM tmptable; dump database tmptable;

しかし、当然のことながら、重複したキーエラーが発生します...

どうすれば防ぐことができますか?

-編集-

私は試した:

CREATE TEMPORARY TABLE tmptable SELECT * FROM blogs WHERE lan = 2;
UPDATE tmptable SET lan = 1;
ALTER TABLE tmptable DROP id;
INSERT INTO blogs SELECT * FROM tmptable; dump database tmptable;

しかし、その後Column count doesn't match value count at row 1

-編集-

私はこれがうまくいくと信じています(そして、いくつのレコードが存在するかを知っているので、うまくいきました)

CREATE TEMPORARY TABLE tmptable SELECT * FROM blogs WHERE lan = 2;
UPDATE tmptable SET lan = 1;
UPDATE tmptable SET id = id + 1000;
INSERT INTO blogs SELECT * FROM tmptable;

しかし、どうすれば適切に行うことができますか?(主キー(id)の次の利用可能な自動インクリメント値を設定するだけです(PHP/alikeなし))

-編集-

多分このようなものですか?

CREATE TEMPORARY TABLE tmptable SELECT * FROM blogs WHERE lan = 2;
UPDATE tmptable SET lan = 1;
UPDATE tmptable SET id = id + (SELECT id FROM blogs ORDER BY id DESC LIMIT 1);
INSERT INTO blogs SELECT * FROM tmptable;
4

5 に答える 5

17

一時テーブルは必要ありません。

INSERT INTO blogs (lan, col1, col2, col3, ...)
SELECT 1, col1, col2, col3, ...
FROM blogs
WHERE lan = 2

col1, col2, col3, ...を除くすべての列のリストに置き換えます。lanid

于 2013-05-09T19:12:28.357 に答える
4
CREATE TEMPORARY TABLE tmptable SELECT * FROM blogs WHERE lan = 2;
UPDATE tmptable SET lan = 1;
alter table tmptable drop column id;
INSERT INTO blogs SELECT NULL,tmptable.* FROM tmptable;

列「id」が最初の列であると仮定します。

于 2013-05-11T23:04:07.353 に答える
1
UPDATE blogs SET lan = 1 WHERE lan = 2;

元のテーブルでそのクエリを実行するだけです。

言語を変更したくありません。すべての記録の別のコピーを保存し、このコピーに別の言語を割り当てたいです

その場合は、一時テーブルから主キーを削除します。行を挿入し直すときは、主キー列を含めないでください。

INSERT INTO blogs (title, lan) SELECT * FROM tmptable;
于 2013-05-09T18:45:12.543 に答える
1

次のSQLを試してください。同様の SQL FIDDLE

 CREATE TEMPORARY TABLE tmptable SELECT * FROM blogs WHERE lan = 2;
    UPDATE tmptable SET lan = 1;
    UPDATE tmptable SET id = (select @val:=@val+1 from(select @val:=(select max(id) from blogs)) t)
    INSERT INTO blogs SELECT * FROM tmptable;

お役に立てれば。

于 2013-05-16T06:34:54.807 に答える
0

準備済みステートメントを使用すると、使用する列の情報スキーマをクエリしてから、実行するクエリを偽造できます。

ここにあなたのケースの例:

-- first query all the blogs column minus id and lan

SELECT GROUP_CONCAT(c.COLUMN_NAME)
INTO @cols
FROM INFORMATION_SCHEMA.COLUMNS c
WHERE
 c.TABLE_NAME = 'blogs'
 AND c.COLUMN_NAME not in ('id', 'lan');

-- second build the query with the gathered columns
-- like INSERT INTO blogs(lan, col1, ...) SELECT 2, col1, ... FROM blogs WHERE lan=1

SET @sql=CONCAT(CONCAT(CONCAT(CONCAT('INSERT INTO blogs (lan,', @cols), 
                ') SELECT 2,'), @cols), ' FROM blogs WHERE lan=1');

-- prepare the statement    
PREPARE stmt FROM @sql;

-- and last run the insert
EXECUTE stmt;
于 2013-05-15T12:05:32.357 に答える