我试图在每个记录(MySQL)的三个不同字段中选择最大日期所以,在每一行中,我有date1,date2和date3:date1总是填充,date2和date3可以是NULL或空GREATEST语句是简单而简洁但对NULL字段没有影响,所以这不能很好地工作:
SELECT id, GREATEST(date1, date2, date3) as datemax FROM mytable
Run Code Online (Sandbox Code Playgroud)
我尝试了更复杂的解决方案,如下所示:
SELECT
CASE
WHEN date1 >= date2 AND date1 >= date3 THEN date1
WHEN date2 >= date1 AND date2 >= date3 THEN date2
WHEN date3 >= date1 AND date3 >= date2 THEN date3
ELSE date1
END AS MostRecentDate
Run Code Online (Sandbox Code Playgroud)
这里的问题相同:返回正确的记录时,NULL值是一个很大的问题
拜托,你有解决方案吗?提前致谢....
Mat*_*dge 94
使用 COALESCE
SELECT id,
GREATEST(date1,
COALESCE(date2, 0),
COALESCE(date3, 0)) as datemax
FROM mytable
Run Code Online (Sandbox Code Playgroud)
更新:以前使用的这个答案IFNULL确实有效,但正如Mike Chamberlain在评论中指出的那样,COALESCE实际上是首选的方法.
ype*_*eᵀᴹ 31
如果date1永远不可能NULL,那么结果永远不应该是NULL,对吧?然后,如果你愿意,你可以利用这一点,NULL日期计算时将不计(或更改1000-01-01到9999-12-31,如果你想空值计算为"地老天荒"):
GREATEST( date1
, COALESCE(date2, '1000-01-01')
, COALESCE(date3, '1000-01-01')
) AS datemax
Run Code Online (Sandbox Code Playgroud)
但是,如果所有日期碰巧都为空怎么办?您仍然希望将 null 作为输出,对吗?那么你需要这个
select nullif(greatest(coalesce(<DATEA>, from_unixtime(0)), coalesce(<DATEB>, from_unixtime(0))), from_unixtime(0));
Run Code Online (Sandbox Code Playgroud)
现在,如果两者都为 null,则得到 null,如果其中之一不为 null,或者两者都不为 null,则得到最大的。
这太疯狂了,特别是如果您要多次使用它,那么您可能希望将其创建为函数,如下所示:
delimiter //
drop function if exists cp_greatest_date//
create function cp_greatest_date ( dateA timestamp, dateB timestamp ) returns timestamp
deterministic reads sql data
begin
# if both are null you get null, if one of them is not null of both of them are not null, you get the greatest
set @output = nullif(greatest(coalesce(dateA, from_unixtime(0)), coalesce(dateB, from_unixtime(0))), from_unixtime(0));
# santiago arizti
return @output;
end //
delimiter ;
Run Code Online (Sandbox Code Playgroud)
然后你可以像这样使用它
select cp_greatest_date(current_timestamp, null);
-- output is 2017-05-05 20:22:45
Run Code Online (Sandbox Code Playgroud)