Joda-Time中两个日期之间的天数

本文翻译自:Number of days between two dates in Joda-Time

How do I find the difference in Days between two Joda-Time DateTime instances? 如何找到两个Joda-Time DateTime实例之间的天数差异? With 'difference in days' I mean if start is on Monday and end is on Tuesday I expect a return value of 1 regardless of the hour/minute/seconds of the start and end dates. “天数差异”是指如果开始时间是星期一而结束时间是星期二,我预计返回值为1,无论开始日期和结束日期的小时/分钟/秒。

Days.daysBetween(start, end).getDays() gives me 0 if start is in the evening and end in the morning. Days.daysBetween(start, end).getDays()如果开始是在晚上并在早上结束,则给出0。

I'm also having the same issue with other date fields so I was hoping there would be a generic way to 'ignore' the fields of lesser significance. 我也和其他日期字段有同样的问题所以我希望有一种通用的方法来“忽略”不太重要的字段。

In other words, the months between Feb and 4 March would also be 1, as would the hours between 14:45 and 15:12 be. 换句话说,2月到3月4日之间的月份也是1,而14:45到15:12之间的时间也是1。 However the hour difference between 14:01 and 14:55 would be 0. 但是,14:01和14:55之间的小时差异为0。


#1楼

参考:https://stackoom.com/question/FxIz/Joda-Time中两个日期之间的天数


#2楼

Annoyingly, the withTimeAtStartOfDay answer is wrong, but only occasionally. 令人讨厌的是,withTimeAtStartOfDay答案是错误的,但只是偶尔。 You want: 你要:

Days.daysBetween(start.toLocalDate(), end.toLocalDate()).getDays()

It turns out that "midnight/start of day" sometimes means 1am (daylight savings happen this way in some places), which Days.daysBetween doesn't handle properly. 事实证明,“午夜/一天的开始”有时意味着凌晨1点(在某些地方以这种方式发生夏令时),Days.daysBetween无法正常处理。

// 5am on the 20th to 1pm on the 21st, October 2013, Brazil
DateTimeZone BRAZIL = DateTimeZone.forID("America/Sao_Paulo");
DateTime start = new DateTime(2013, 10, 20, 5, 0, 0, BRAZIL);
DateTime end = new DateTime(2013, 10, 21, 13, 0, 0, BRAZIL);
System.out.println(daysBetween(start.withTimeAtStartOfDay(),
                               end.withTimeAtStartOfDay()).getDays());
// prints 0
System.out.println(daysBetween(start.toLocalDate(),
                               end.toLocalDate()).getDays());
// prints 1

Going via a LocalDate sidesteps the whole issue. 通过LocalDate回避整个问题。


#3楼

public static int getDifferenceIndays(long timestamp1, long timestamp2) {
    final int SECONDS = 60;
    final int MINUTES = 60;
    final int HOURS = 24;
    final int MILLIES = 1000;
    long temp;
    if (timestamp1 < timestamp2) {
        temp = timestamp1;
        timestamp1 = timestamp2;
        timestamp2 = temp;
    }
    Calendar startDate = Calendar.getInstance(TimeZone.getDefault());
    Calendar endDate = Calendar.getInstance(TimeZone.getDefault());
    endDate.setTimeInMillis(timestamp1);
    startDate.setTimeInMillis(timestamp2);
    if ((timestamp1 - timestamp2) < 1 * HOURS * MINUTES * SECONDS * MILLIES) {
        int day1 = endDate.get(Calendar.DAY_OF_MONTH);
        int day2 = startDate.get(Calendar.DAY_OF_MONTH);
        if (day1 == day2) {
            return 0;
        } else {
            return 1;
        }
    }
    int diffDays = 0;
    startDate.add(Calendar.DAY_OF_MONTH, diffDays);
    while (startDate.before(endDate)) {
        startDate.add(Calendar.DAY_OF_MONTH, 1);
        diffDays++;
    }
    return diffDays;
}

#4楼

The accepted answer builds two LocalDate objects, which are quite expensive if you are reading lot of data. 接受的答案构建了两个LocalDate对象,如果您正在阅读大量数据,这些对象非常昂贵。 I use this: 我用这个:

  public static int getDaysBetween(DateTime earlier, DateTime later)
  {
    return (int) TimeUnit.MILLISECONDS.toDays(later.getMillis()- earlier.getMillis());
  }

By calling getMillis() you use already existing variables. 通过调用getMillis()您可以使用已存在的变量。
MILLISECONDS.toDays() then, uses a simple arithmetic calculation, does not create any object. MILLISECONDS.toDays()然后,使用简单的算术计算,不创建任何对象。


#5楼

你可以使用LocalDate

Days.daysBetween(new LocalDate(start), new LocalDate(end)).getDays() 

#6楼

Days Class Days

Using the Days class with the withTimeAtStartOfDay method should work: 使用带有withTimeAtStartOfDay方法的Days类应该可以:

Days.daysBetween(start.withTimeAtStartOfDay() , end.withTimeAtStartOfDay() ).getDays() 
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值