获取一天开始的时间戳

时间:2012-12-15 12:26:34

标签: android

我使用unix时间戳在数据库中存储时间/日期。 我想在某一天获取所有实例,因此我需要计算当天开始的时间戳,以便查询数据库。

我在php中做了类似的事情,通过传递mktime日期/月/年的值从日期对象并将小时和分钟设置为零。在java / android中似乎没有类似的功能(获取日期的特定部分的函数已弃用)

有人可以给出一些指导吗?感谢

修改

好的,所以我意识到这可能有用:

public static int startOfDay(Timestamp time) {
        Calendar cal = dateToCalendar(new Date(time.getTime()));
        cal.add(Calendar.HOUR_OF_DAY, -Calendar.HOUR_OF_DAY);
        cal.add(Calendar.MINUTE, -Calendar.MINUTE);
        cal.add(Calendar.SECOND, -Calendar.SECOND);
        Log.i("Time", cal.getTime().toString());        
        return (int) cal.getTimeInMillis()/1000;
}

然而,当我刚刚运行时,我得到了:

Sat Dec 15 01:24:00 GMT 2012

秒是正确的但是小时和分钟是错的?

3 个答案:

答案 0 :(得分:39)

在处理时间时,您应该始终考虑时区。您的数据库时间戳应始终存储在一个时区(例如UTC)中。然后,您的计算应该考虑用户可以处于不同的时区,并且他们可以更改时区。

如果您想计算用户当前在手机中设置的时区中的一天的开始时间。使用以下命令创建Calendar实例

Calendar cal = Calendar.getInstance(); 

要获取特定时区的实例,请使用:

// use UTC time zone
Calendar cal = Calendar.getInstance(TimeZone.getTimeZone("UTC"));

然后设置当天的开头:

cal.setTime(time); // compute start of the day for the timestamp
cal.set(Calendar.HOUR_OF_DAY, 0);
cal.set(Calendar.MINUTE, 0);
cal.set(Calendar.SECOND, 0);
cal.set(Calendar.MILLISECOND, 0);

答案 1 :(得分:7)

public static int startOfDay(Timestamp time) {
    Calendar cal = Calendar.getInstance();
    cal.setTimeInMillis(time.getTime());
    cal.set(Calendar.HOUR_OF_DAY, 0); //set hours to zero
    cal.set(Calendar.MINUTE, 0); // set minutes to zero
    cal.set(Calendar.SECOND, 0); //set seconds to zero
    Log.i("Time", cal.getTime().toString());        
    return (int) cal.getTimeInMillis()/1000;
}

答案 2 :(得分:3)

TL;博士

ZoneId z = ZoneId.of( "America/Montreal" );
long secondsSinceEpoch = ZonedDateTime.now( z ).toLocalDate().asStartOfDay( z ).toEpochSecond() ;

详细

接受的Answer by Tomik是正确但过时的。麻烦的旧遗留日期时间类已被java.time类取代。

正如该答案建议的那样,您必须在开始一天时考虑时区。时区对于确定日期至关重要。对于任何给定的时刻,日期在全球范围内因地区而异。例如,法国巴黎午夜过后几分钟,在魁北克蒙特利尔的“昨天”仍然是新的一天。

ZoneId z = ZoneId.of( "America/Montreal" );
ZonedDateTime zdt = ZonedDateTime.now( z );

获得当天的第一时刻需要通过LocalDateLocalDate类表示没有时间且没有时区的仅限日期的值。

LocalDate today = zdt.toLocalDate();
ZonedDateTime zdtTodayStart = today.atStartOfDay( z );

请注意,我们让java.time确定一天的开始,而不是假设和硬编码00:00:00。由于夏令时(DST)和其他异常,这一天可能会在01:00:00等其他时间开始。

显然,unix timestamp表示自1970年第一个UTC以来的整秒数。 ZonedDateTime类有一个方法可以为您提供该号码。请注意,这可能意味着数据丢失,因为ZonedDateTime可能只有几分之一秒,分辨率为纳秒。

long secondsSinceEpoch = zdtTodayStart.toEpochSecond();

关于 java.time

java.time框架内置于Java 8及更高版本中。这些类取代了麻烦的旧legacy日期时间类,例如java.util.DateCalendar和& SimpleDateFormat

现在位于Joda-Timemaintenance mode项目建议迁移到java.time类。

要了解详情,请参阅Oracle Tutorial。并搜索Stack Overflow以获取许多示例和解释。规范是JSR 310

您可以直接与数据库交换 java.time 对象。使用符合JDBC driver或更高版本的JDBC 4.2。不需要字符串,不需要java.sql.*类。

从哪里获取java.time类?