我在mySQL(DATETIME
)中有一个fromStamp
字段,其中包含有效的日期/时间戳。
我需要能够将分钟数提升到下一个6分钟的间隔。秒应忽略或视为:00
因此,如果我的DATETIME为2013-01-31 13:07:17
,我需要将结果设为2013-01-31 13:12:00
除了介于:00和:06之间以及:31和:36之间的时间需要舍入 DOWN 。
:00-06 round DOWN to 00
:07-12 round UP to 12
:13-18 round UP to 18
:19-24 round UP to 24
:24-30 round UP to 30
:31-36 round DOWN to 30
:37-42 round UP to 42
:43-48 round UP to 48
:49-54 round UP to 54
:55-00 round UP to 00
我找到了一种合理的方式来选择性地向下舍入:
SELECT
fromStamp,
CONCAT(DATE_FORMAT(`fromStamp`, '%Y-%m-%d'), ' ',
SEC_TO_TIME((TIME_TO_SEC(`fromStamp`) DIV 360) * 360))
FROM `table`
WHERE (
DATE_FORMAT(`fromStamp`, '%i') BETWEEN 0 AND 6
OR DATE_FORMAT(`fromStamp`, '%i') BETWEEN 31 AND 36
);
是否有一种很好的方法可以将其他所有内容四舍五入到下一个6分钟的间隔? (我觉得我错过了一些简单的事情)
更新
所以我要使用@ mellamokb的解决方案,但他的评论认为秒是正确的,它确实发挥作用。
2013-01-22 12:24:13的日期时间到12:30,这不是我需要的,所以我先做:
UPDATE table SET fromStamp = CONCAT(DATE_FORMAT(fromStamp, '%Y-%m-%d %h:%i'), ':00');
摆脱秒,然后他的查询得到我正在寻找的东西。
答案 0 :(得分:2)
向上舍入是非常相似的逻辑,除了您添加1
以转移到下一个最近的6-minute
间隔。我还从1
中减去TIME_TO_SEC
作为更正因素,否则06:00
等临界值会在接下来的6分钟间隔内向上移动,即12:00
SEC_TO_TIME( ( (TIME_TO_SEC(`fromStamp`) - 1) DIV 360 + 1) * 360))
^^^ add one
要合并两者,请使用CASE
语句来控制每条记录使用哪种舍入方式:
SELECT
fromStamp,
CASE WHEN
DATE_FORMAT(`fromStamp`, '%i') BETWEEN 0 AND 6
OR DATE_FORMAT(`fromStamp`, '%i') BETWEEN 31 AND 36
THEN
CONCAT(DATE_FORMAT(`fromStamp`, '%Y-%m-%d'), ' ',
SEC_TO_TIME((TIME_TO_SEC(`fromStamp`) DIV 360) * 360))
ELSE
CONCAT(DATE_FORMAT(`fromStamp`, '%Y-%m-%d'), ' ',
SEC_TO_TIME(((TIME_TO_SEC(`fromStamp`) - 1) DIV 360 + 1) * 360))
END
FROM `table`
(DEMO)
答案 1 :(得分:1)
根据提供的标准,我认为处理这种奇怪类型舍入的最简单方法是:
SELECT `fromStamp`
, DATE_FORMAT(`fromStamp`,'%Y-%m-%d %H') + INTERVAL
CASE
WHEN TIME_FORMAT(`fromStamp`,'%i') <= 6 THEN 0 -- round DOWN
WHEN TIME_FORMAT(`fromStamp`,'%i') <= 12 THEN 12 -- round up
WHEN TIME_FORMAT(`fromStamp`,'%i') <= 18 THEN 18 -- round up
WHEN TIME_FORMAT(`fromStamp`,'%i') <= 24 THEN 24 -- round up
-- WHEN TIME_FORMAT(`fromStamp`,'%i') <= 30 THEN 30 -- round up
WHEN TIME_FORMAT(`fromStamp`,'%i') <= 36 THEN 30 -- round DOWN
WHEN TIME_FORMAT(`fromStamp`,'%i') <= 42 THEN 42 -- round up
WHEN TIME_FORMAT(`fromStamp`,'%i') <= 48 THEN 48 -- round up
WHEN TIME_FORMAT(`fromStamp`,'%i') <= 54 THEN 54 -- round up
WHEN TIME_FORMAT(`fromStamp`,'%i') >= 55 THEN 60 -- round up
END MINUTE AS rnd_fromStamp
这似乎是表达正在发生的事情的最直接的方式,对于那些看过这个陈述的未来评论者来说,并且想知道“这些声明是什么塑料来自theStamp?”
可能会有更快(更高效)的算法,但我认为这些算法不会更优雅,或者更容易理解和理解。
答案 2 :(得分:0)
这用于最后一分钟
选择 MINUTE(SEC_TO_TIME(((TIME_TO_SEC(call_duration))DIV 60 +1)* 60)) call_duration 从 call_log