You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Android Room查询日期范围时如何包含结束日期?

解决Room查询不包含结束日任务的问题

你的问题核心是:用BETWEEN :from AND :to查询时,结束日当天的任务因为start_time(比如4月30日10点的时间戳)大于to(4月30日0点的时间戳),所以被排除了。这里给你两种靠谱的解决方法:

方法一:调整查询条件,用「小于结束日下一天0点」替代「小于等于结束日0点」

修改DAO的查询语句,把BETWEEN改成范围判断,确保包含结束日当天所有时间的任务:

@Query("SELECT * FROM tasks WHERE start_time >= :from AND start_time < :toExclusive")
List<TimeEntity> getChoosenTimes(long from, long toExclusive);

调用这个方法时,把用户选择的结束日期加一天,转成对应时间戳(比如用Java的LocalDate或者Calendar处理):

// 假设用户选的结束日期是endDate(LocalDate类型)
long toExclusive = endDate.plusDays(1).atStartOfDay(ZoneId.systemDefault()).toInstant().toEpochMilli();

这种方式用时间戳直接比较,数据库查询效率最高,还能避免夏令时等时间计算问题。

方法二:用SQLite日期函数直接比较日期

如果不想修改传入的参数,也可以利用SQLite的日期函数,把时间戳转成日期字符串再比较,这样不管start_time是当天的哪个时刻,都会被纳入结束日的范围:

@Query("SELECT * FROM tasks WHERE date(start_time / 1000, 'unixepoch') BETWEEN date(:from / 1000, 'unixepoch') AND date(:to / 1000, 'unixepoch')")
List<TimeEntity> getChoosenTimes(long from, long to);

注意这里要把毫秒级时间戳除以1000转成秒级,因为SQLite的unixepoch是基于秒的。这种方式可读性更强,适合数据量不大的场景。

为什么原来的语句不行?

你用TypeConverter把日期转成Long存储时,选的结束日期(比如4月30日)对应的是当天0点的时间戳,但任务的start_time是任务实际开始的时间(比如4月30日14:30),这个时间戳肯定比0点的大,所以BETWEEN会把它排除在外。

内容的提问来源于stack exchange,提问作者steeveKA1

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.25 00:42:01