我有一台PostgreSQL 8.4服务器,每晚01:00重新启动(不要问),需要获得连接用户的列表(即他们的时间戳是u.login > u.logout
):
SELECT u.login, u.id, u.first_name
FROM pref_users u
WHERE u.login > u.logout and
u.login > now() - interval '24 hour'
ORDER BY u.login;
login | id | first_name
----------------------------+----------------+-------------
2012-03-14 09:27:33.41645 | OK171511218029 | Alice
2012-03-14 09:51:46.387244 | OK448670789462 | Bob
2012-03-14 09:52:36.738625 | OK5088512947 | Sergej
但比较u.login > now()-interval '24 hour'
也会在最后01:00之前交付用户,这很糟糕,尤其是在早上。
有没有什么有效的方法可以获取自上次01:00以来的登录信息,而不使用to_char()
进行字符串杂技?
这应该是1)正确的,2)尽可能快:
SELECT u.login, u.id, u.first_name
FROM pref_users u
WHERE u.login >= now()::date + interval '1h'
AND u.login > u.logout
ORDER BY u.login;
由于您的表中没有未来的时间戳(我想),因此您不需要上限。
一些等价的表达式:
SELECT localtimestamp::date + interval '1h'
, current_date + interval '1h'
, date_trunc('day', now()) + interval '1h'
, now()::date + interval '1h'
在旧版本中,now()::date
的执行速度曾经略高于CURRENT_DATE
,但在现代Postgres中,这已经不再是事实了。但由于某种原因,两者中的任何一个仍然比Postgres14中的LOCALTIMESTAMP
快。
CCD_ 7在返回CCD_。但与timestamp
列login
相比,根据当前会话的timezone
设置,它被强制为timestamp
,有效地做到了同样的效果。
参见:
- 在Rails和PostgreSQL中完全忽略时区
若要在当地时间00:00至01:00之间发布时返回前一天的行而不返回任何内容,请改用:
WHERE u.login >= (LOCALTIMESTAMP - interval '1h')::date + interval '1h'
select * from termin where DATE(dateTimeField) >= CURRENT_DATE AND DATE(dateTimeField) < CURRENT_DATE + INTERVAL '1 DAY'
这对我很有用——它选择了所有具有"今日日期"的行。
select * from termin where DATE(dateTimeField) = '2015-11-17'
这对我很管用!
从01:00开始只获取当天时间戳的一种简单方法是使用CURRENT_DATE + interval '1 hour'
所以你的查询应该是这样的:
SELECT u.login, u.id, u.first_name
FROM pref_users u
WHERE u.login > u.logout AND
u.login > CURRENT_DATE + interval '1 hour'
ORDER BY u.login;
希望能有所帮助。
where
u.login > u.logout
and
date_trunc('day', u.login) = date_trunc('day', now())
and
date_trunc('hour', u.login) >= 1
到目前为止,所有答案都是不正确的,因为它们给出的答案在0.00到1.00之间是错误的。因此,如果您碰巧在该时间段内运行查询,则不会得到任何结果。根据@ErwinBrandstetter的回答,你想要的是:
WHERE u.login > u.logout
AND u.login >= CASE WHEN NOW()::time < '1:00'::time THEN NOW()::date - INTERVAL '23 HOUR' ELSE NOW()::date + INTERVAL '1 HOUR' END;
我很想在没有条件的情况下做,但没有找到办法。
编辑:@ErwinBrandstetter确实在没有条件的情况下做了这件事,为了完整起见,把它留在这里。