我正在寻找一个干净的解决方案来格式化带有可选部分的Date个对象。我的日期对象可以是时间戳值,仅时间值或仅日期值。
我想像这样显示日期值:
如果日期的ms value小于(86400 * 1000),则表示该值实际上是一个仅限时间的值。如果是这样显示:
HH:mm:ss.SSS
如果日期的值恰好是午夜,则表示它是仅限日期的值。如果是这样显示:
yyyy-MM-dd
否则显示如下:
yyyy-MM-dd HH:mm:ss.SSS
不幸的是我正在使用Date
作为输入。无法改变。我只对格式化/渲染感兴趣,而不是解析。外部图书馆在我的组织中很难卖。
为了格式化,当然可以接受首先转换为新的Java 8日期/时间对象之一,如果这样可以使解决方案更简单。
平台:Java 8 SE
答案 0 :(得分:3)
将Date
转换为Java 8等效结构:
private static TemporalAccessor toJava8Time(Date date) {
Instant instant = date.toInstant();
if (instant.isBefore(Instant.ofEpochSecond(86400))) {
return instant.atZone(ZoneId.systemDefault()).toLocalTime();
} else if (instant.equals(instant.truncatedTo(ChronoUnit.HOURS))) {
return instant.atZone(ZoneId.systemDefault()).toLocalDate();
} else {
return instant.atZone(ZoneId.systemDefault()).toLocalDateTime();
}
}
创建一个足够通用的格式化程序,以根据需要对LocalTime
,LocalDate
和LocalDateTime
进行字符串化:
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("[yyyy-MM-dd] [HH:mm:ss]");
Date time = new Date(39733000L); // 1970-01-01T12:02:13
Date date = new Date(1462399200000L); // 2016-05-05T00:00:00
Date dateTime = new Date(1462442533000L); // 2016-05-05T12:02:13
Stream.of(time, date, dateTime)
.map(d -> toJava8Time(d))
.map(t -> formatter.format(t).trim())
.forEach(System.out::println);
//Outputs "12:02:13", "2016-05-05", "2016-05-05 12:02:13"
注意:我必须拨打trim()
,否则时间会以空格开头。
答案 1 :(得分:1)
而不是java.util.Date
使用java.time
包中的相应类。这意味着您可以为LocalDate
,LocalTime
或LocalDateTime
明确地设置单独的方法,并使代码更清晰。
现在,如果你遇到java.util.Date
并且你无能为力,你应该使用getTime()
方法(你已经知道的)来决定{{3}每种输出类型的实现。
答案 2 :(得分:0)
您可以尝试导入并使用与此类似的SimpleDateFormat
:
import java.sql.Time;
public class Example {
public static void main(String[] args) {
Time ex = new Time( Date.getTime() ); //param: long
System.out.println(ex.toString()); // prints 00:05:28
}
}
编辑:Joe C的解决这个问题的方法可以说比我的实现更好。
答案 3 :(得分:0)
我认为你需要多个SimpleDateFormat对象。您的代码可能如下所示:
SimpleDateFormat timeOnlySdf = new SimpleDateFormat( "HH:mm:ss.SSS");
SimpleDateFormat dateOnlySdf = new SimpleDateFormat( "yyyy-MM-dd");
SimpleDateFormat dateAndTimeSdf = new SimpleDateFormat( "yyyy-MM-dd HH:mm:ss.SSS");
Date epochPlusOne = new Date( 86400 * 1000);
Calendar cal = Calendar.getInstance();
cal.setTime( myDate);
if( myDate.before( epochPlusOne))
{
System.out.println( timeOnlySdf.format( myDate));
}
else if( cal.get( Calendar.HOUR) == 0 &&
cal.get( Calendar.MINUTE) == 0 &&
cal.get( Calendar.SECOND) == 0 &&
cal.get( Calendar.MILLISECOND) == 0)
{
System.out.println( dateOnlySdf.format( myDate));
}
else
{
System.out.println( dateAndTimeSdf.format( myDate));
}