web-dev-qa-db-ja.com

mysqlは同じnow()で複数の列を更新します

2つのdatetimeカラムを更新する必要がありますが、mysqlバージョン4.1.20を使用して、それらをまったく同じにする必要があります。私はこのクエリを使用しています:

mysql> update table set last_update=now(), last_monitor=now() where id=1;

now()?の2つの目に見える呼び出しのために、安全であるか、列が異なる時間で更新される可能性があります。
異なる値で更新できるとは思いません(内部的にmysqlは行ごとに一度だけnow()を呼び出すと思います)が、私はエキスパートではありません、どう思いますか?

更新:2番目の質問が抽出されました ここ

77
Radu Maris

ソリューションを見つけました:

mysql> UPDATE table SET last_update=now(), last_monitor=last_update WHERE id=1;

MySQL Docsで this を見つけ、いくつかのテストを行った後、動作します。

次の文は、col2を元のcol1値ではなく現在の(更新された)col1値に設定します。その結果、col1とcol2の値は同じになります。この動作は、標準SQLとは異なります。

UPDATE t1 SET col1 = col1 + 1、col2 = col1;

129
Radu Maris

Mysqlはあまり賢くありません。複数の更新クエリまたは挿入クエリで同じタイムスタンプを使用する場合は、変数を宣言する必要があります。

now()関数を使用すると、システムは別のクエリで呼び出すたびに現在のタイムスタンプを呼び出します。

7
Olivier

MySQLは、ステートメントの実行開始時にステートメントごとに1回now()を評価します。そのため、ステートメントごとに複数の可視now()呼び出しを持つことは安全です。

select now(); select now(), sleep(10), now(); select now();
+---------------------+
| now()               |
+---------------------+
| 2018-11-05 16:54:00 |
+---------------------+
1 row in set (0.00 sec)

+---------------------+-----------+---------------------+
| now()               | sleep(10) | now()               |
+---------------------+-----------+---------------------+
| 2018-11-05 16:54:00 |         0 | 2018-11-05 16:54:00 |
+---------------------+-----------+---------------------+
1 row in set (10.00 sec)

+---------------------+
| now()               |
+---------------------+
| 2018-11-05 16:54:10 |
+---------------------+
1 row in set (0.00 sec)
1
Rich Andrews

タイムスタンプ列のデフォルト値に次のコードを配置できます:CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP。したがって、更新すると2つの列は同じ値を取ります。

1
Danny

更新クエリを実行する前に、now()の値を変数に保存し、その変数を使用して、フィールドlast_updatelast_monitorの両方を更新できます。

これにより、now()が一度だけ実行され、必要な両方の列で同じ値が更新されます。

1
Sachin Shanbhag

これには2つの方法があります。

First、sqlステートメントに挿入する前にnow()を変数として宣言することをお勧めします。まあ言ってみれば;

var x = now();
mysql> UPDATE table SET last_update=$x, last_monitor=$x WHERE id=1;

論理的に、last_monitorに別の入力が必要な場合は、次のような別の変数を追加します。

var y = time();
mysql> UPDATE table SET last_update=$x, last_monitor=$y WHERE id=1;

このように、mysqlステートメントだけでなく、プロジェクトで使用しているサーバー側スクリプト言語(PHPなど)でも変数を何度でも使用できます。これらの同じ変数を、アプリケーションのフロントエンドのフォームに入力として挿入できることに注意してください。これにより、プロジェクトが静的ではなく動的になります。

Secondly now()が更新時間を示す場合、mysqlを使用して、行のプロパティをタイムスタンプとしてデカールできます。行が挿入または更新されるたびに、時間も更新されます。

0
Wahinya Brian

now()が同じ値を持っていることを本当に確認する必要がある場合は、2つのクエリを実行できます(2番目の質問にも答えます。その場合、update last_monitor = to last_updatelast_updateまだ更新されていません)

次のようなことができます:

mysql> update table set last_update=now() where id=1;
mysql> update table set last_monitor = last_update where id=1;

とにかく、mysqlはnow()をクエリごとに1回だけ要求するのに十分だと思います。

0
sathia