我有一个MySQL(v 5,MyISAM)查询,根据日期字符串格式返回不同的行。
(1) IFNULL(date1, ADDDATE('2008/10/31 23:59:59',INTERVAL 1 DAY)) > '2008-10-31 23:59:59'
(2) IFNULL(date1, ADDDATE('2008/10/31 23:59:59',INTERVAL 1 DAY)) > '2008/10/31 23:59:59'
(3) date1 > '2008-10-31 23:59:59'
(4) date1 > '2008/10/31 23:59:59'
'/'vs' - '关于'>'的RHS'比较算子。
(1) 75,098 rows *expected*
(2) 0 rows *DIFFERENCE*
(3) 199 rows *simple case as expected*
(4) 199 rows *simple case as expected*
问题 - 为什么?
答案 0 :(得分:2)
简短回答:
使用CAST(... AS DATE)
答案很长:
允许使用“宽松”语法:任何 标点字符可以用作 日期部分之间的分隔符或 时间部分。例如,'98 -12-31 11:30:45','98 .12.31 11 + 30 + 45', '98 / 12/31 11 * 30 * 45'和'98 @ 12 @ 31 11 ^ 30 ^ 45'是等价的。
在您的示例1和2中,您正在使用ADDDATE ...无论输入格式是什么,这将始终返回带有“ - ”分隔符的日期:
+-----------------------------------------------+
| ADDDATE('2008/10/31 23:59:59',INTERVAL 1 DAY) |
+-----------------------------------------------+
| 2008-11-01 23:59:59 |
+-----------------------------------------------+
您还使用了IFNULL,它会丢失类型信息,因此当您比较它时,它会比较为字符串。
你能做的就是把它重新投入日期:
mysql> SELECT IFNULL(null, ADDDATE('2008/10/31 23:59:59',INTERVAL 1 DAY)) > '2008/10/31 23:59:59';
+-------------------------------------------------------------------------------------+
| IFNULL(null, ADDDATE('2008/10/31 23:59:59',INTERVAL 1 DAY)) > '2008/10/31 23:59:59' |
+-------------------------------------------------------------------------------------+
| 0 |
+-------------------------------------------------------------------------------------+
1 row in set (0.00 sec)
mysql> SELECT CAST(IFNULL(null, ADDDATE('2008/10/31 23:59:59',INTERVAL 1 DAY)) AS DATE) > '2008/10/31 23:59:59';
+---------------------------------------------------------------------------------------------------+
| CAST(IFNULL(null, ADDDATE('2008/10/31 23:59:59',INTERVAL 1 DAY)) AS DATE) > '2008/10/31 23:59:59' |
+---------------------------------------------------------------------------------------------------+
| 1 |
+---------------------------------------------------------------------------------------------------+
答案 1 :(得分:0)
我对mysql了解不多,但基于“/”的日期是否可能被解释为“YYYY / DD / MM”,因此完全无效?在SQL Server中,我希望在这种情况下会出现异常,但如果mysql替换了某种“无效日期”值,这可能会解释差异。
YYYY-MM-DD是官方ISO格式。 YYYY / MM / DD我从未听说过。
答案 2 :(得分:0)
参考简答:使用CAST(... AS DATE)
LHS与(1)和(2)相同,它是改变评估的RHS,也是一个字符串。
参考“/”基于日期。
如果'2008/10/31 23:59:59'是一个无效的日期,它将在选项(1),(3),(4)中失败,这是唯一的一个。 如果''2008-10-31 23:59:59'是一个无效的日期,它将在选项(1),(3)中失败,并且成功。