参考
11.2.6 Out-of-Range and Overflow Handling
http://dev.mysql.com/doc/refman/5.5/en/out-of-range-and-overflow.html
BIGINT UNSIGNED value is out of rangeとかいうエラーが出たり出なかったりで困ってるとかいう話がふときたのでここにつらつらと書いておく
こんなテーブルがあるとする
| test | CREATE TABLE `test` (
`col1` int(10) unsigned NOT NULL DEFAULT '0',
`col2` bigint(20) unsigned NOT NULL DEFAULT '0',
PRIMARY KEY (`col1`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8
こんなデータが入っていたとする
mysql> select * from test;
+------+------+
| col1 | col2 |
+------+------+
| 1 | 3 |
+------+------+
1 row in set (0.00 sec)
こんなクエリが流れてるとする
mysql> update test set col2 = IF(col2 - 4 < 0, 0 , col2 - 4) where col1 = 1;
やりたいことはわかる。col2を何らかの数で引きたいけど負になる場合は0を入れとくと。
しかしこれは以下のようなエラーが出る
ERROR 1690 (22003): BIGINT UNSIGNED value is out of range in '(`test`.`test`.`col2` - 4)'
マニュアルには、片方がunsignedの場合、引き算の結果はunsignedになると書かれている。
そしてMySQL5.5.5以前では、結果が負になるときmaximum integer valueになる。
MySQL5.5.5以降では、エラーになる(ERROR 1690 (22003): BIGINT UNSIGNED value is out of range)と書かれている。
以下のようなクエリならOK
update test set col2 = IF(col2 < 4, 0 , col2 - 4) where col1 = 1;
update test set col2 = col2 - IF(col2 < 4, col2 , 4) where col1 = 1;