所以,它是2015年1月26日,我在Android设备上运行以下代码;
GregorianCalendar date = new GregorianCalendar();
SimpleDateFormat df = new SimpleDateFormat();
// Set date to 4 weeks ago, and then use it for the first BETWEEN date in the above query
date.set(GregorianCalendar.WEEK_OF_YEAR, date.get(GregorianCalendar.WEEK_OF_YEAR)-4);
System.out.println(df.format(new Date(date.getTimeInMillis())));
// Set date to 2 weeks time, and then use it for the second BETWEEN date in the above query
date.set(GregorianCalendar.WEEK_OF_YEAR, date.get(GregorianCalendar.WEEK_OF_YEAR)+6);
System.out.println(df.format(new Date(date.getTimeInMillis())));
我得到了输出;
29/12/14 10:29
09/02/14 10:29
在Windows计算机上的标准Java上运行此代码段会显示正确的结果,第二个日期为09/02/15 10:29
。所以在Android上,当我们要求日期回到4周时,正确地滚动年份,但是当我们要求它提前6周(超过我们的原始日期)时,它不会再次向前滚动。 / p>
我在5.0.2和4.4.2
上观察到了这一点所以问题是,这是一个错误还是某种错综复杂的预期行为(功能)?
答案 0 :(得分:2)
您不应该使用Calendar.set
。您正在尝试将周字段设置为无效值,并希望它可以找出您的预期含义。这可能适用于桌面JVM,但你不应该依赖它 - 显然 - Android的实现确实以不同的方式处理它。
使用Calendar.add
代替实际执行的操作:通过适当的调整从字段中添加或减去。
date.add(GregorianCalendar.WEEK_OF_YEAR, -4);
date.add(GregorianCalendar.WEEK_OF_YEAR, 6);
答案 1 :(得分:2)
我非常确定如何计算和处理某些Calendar
字段以及 错误的复杂性。您使用算术调整而不是使用add(...)
方法这一事实可能也会使事情变得复杂。
来自文档...
一个月或一年的第一周定义为从getFirstDayOfWeek()开始并且至少包含该月或年的getMinimalDaysInFirstWeek()天的最早七天。
在这种情况下,一年中的第一周,即WEEK_OF_YEAR = 1
,从1月4日或5日开始,具体取决于一周的第一天是否分别设置为星期日或星期一。
Calendar
类是抽象的,扩展它的具体类的不同实现可能表现不同,但允许在一年内有一个0或甚至-1的索引。日期1 - >的事实第3或第1 - >第4天(取决于一周的第一天)明显落在2015年内意味着从12月28日或29日开始的那一周被归类为第0周。
1月26日属于WEEK_OF_YEAR = 4
(无论是一周的第一天),因此当您从当前WEEK_OF_YEAR
中减去4时,它返回0并将该日期调整为该周的星期一,即12月29日。
当您在之前调整的日期中添加6周时出现问题 - 此时它是2014年12月29日。正如我所说,您正在使用算术调整而不是使用add(...)
方法。由于您未手动调整年份,因此假设它应保持在2014年内,并且通过增加6周您导致溢出/回滚到2014年初,而不是动态调整YEAR
以及WEEK_OF_YEAR
等。