2012-04-04 16 views
1

私はMySQL InnoDBを使用しています。MySQL - 単一のクエリで列が更新されるシーケンス

テーブルを更新し、各列が更新される順序を制御したいと考えています。可能であれば、すべて1つのクエリで理由は、私はゲームのキューシステムを持っているということです。 queue_1を終了すると、queue_2の値が割り当てられ、次にqueue_2が消去されます。

今、私はこれから予期せぬ結果を得ています。ときにはtotal_price_2がゼロに設定され、その後total_price_1にロードされます。どちらもゼロになります。 (私が望むものではない)

私は、DBがアップデートを実行する順序を決定することを読んだ。私は2つの更新を行う必要がある場合、それはいいです。私の目標はパフォーマンスです。

UPDATE 
queue 
SET  
queue_1 = queue_2, 
total_price_1 = total_price_2, 
total_wait_1 = total_wait_2, 
queue_2 = '', 
total_price_2 = 0, 
total_wait_2 = 0 
WHERE id IN(1,2,3) 
+1

アップデート前に 'total_price_2'が' 0'になっていませんか? – MichaelRushton

+0

@MichaelRushton良い考え。あなたのコメントの後、私は自分のクエリではなく、自然な文脈の中でコードを試しています。 7回試して、その都度作業しています。私はそれを与える順序を使用しています。私は嗅覚を守り、ポストバックするつもりです。 – Dor1000

+0

更新前と更新後にキューデータを選択してエコーしました。私のアップデートは予定どおりに動作していたが、それ以外のものは後で値を変更していた。キセノンはこれに関して良い答えを持っています。 – Dor1000

答えて

2

MichaelRushtonのように、更新前にが0ではないことを確認してください。

単一テーブルUPDATE割り当ては通常、左から右に評価されます:MySQLで

は、単一テーブル UPDATEクエリは UPDATE声明文書に記載されている、「左」から処理されます。複数テーブルの更新の場合、特定の順序で割り当てが行われるという保証はありません。 ( Source

具体的には、この例に注意してください。

次の文の2番目の割り当ては、現在の(更新)COL1値ではなく、元のCOL1の値にCOL2を設定します。その結果、col1とcol2は同じ値になります。この動作は標準SQLとは異なります。

:サイドノートのビットとして


側注

UPDATE t1 SET col1 = col1 + 1, col2 = col1; 
、あなたはまた、明示的 ORDER BY句を使用して更新するために順序を指定することができます

WHERE句がない場合、すべての行が更新されます。 ORDER BY句を指定すると、指定された順序で行が更新されます。 (Source

0

queue_1queue_2のためにあなたの更新クエリを分割します。

それが値を更新したときに、MySQLは混乱してしまいますし、それはあなたの結果0を行っている、queue_1queue_2を更新するためqueue_1queue_2、 のための別のための1つの更新クエリを作成します。

0

それはあなたがThis behavior differs from standard SQLによって暗示のようなサーバーに依存する動作に応じている場合は、あなたが将来的に注意する必要があることは注目に値します。 DBを変更するとどうなりますか?あるいは、誰かが注文の重要性を認識せずにそのコードを更新しますか?

更新プログラムを2つの明確なステートメントに分割し、トランザクションを使用してアトミックに実行する方がよい場合があります。

+0

良い点。私は将来の参照のために、自分のプロジェクトでメモを取るテキストファイルを持っています。移行キューはMySQL用にコーディングされているというメモを追加します。シーケンスに影響を受けやすいコードにコメントを追加します。ありがとうCylindric。 – Dor1000

関連する問題