我在服务器中生成的某个日志文件中有毫秒数,我也知道生成日志文件的区域设置,我的问题是将指定格式的毫秒转换为日期.该日志的处理发生在位于不同时区的服务器上.转换为"SimpleDateFormat"程序时,机器的日期是这样的,因为这样的格式化日期并不代表服务器的正确时间.有没有办法优雅地处理这个问题?
long yourmilliseconds = 1322018752992l;
//1322018752992-Nov 22, 2011 9:25:52 PM
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss,SSS",Locale.US);
GregorianCalendar calendar = new GregorianCalendar(TimeZone.getTimeZone("US/Central"));
calendar.setTimeInMillis(yourmilliseconds);
System.out.println("GregorianCalendar -"+sdf.format(calendar.getTime()));
DateTime jodaTime = new DateTime(yourmilliseconds,
DateTimeZone.forTimeZone(TimeZone.getTimeZone("US/Central")));
DateTimeFormatter parser1 = DateTimeFormat.forPattern("yyyy-MM-dd HH:mm:ss,SSS");
System.out.println("jodaTime "+parser1.print(jodaTime));
Run Code Online (Sandbox Code Playgroud)
输出:
Gregorian Calendar -2011-11-23 08:55:52,992
jodaTime 2011-11-22 21:25:52,992
Run Code Online (Sandbox Code Playgroud)
ada*_*ost 253
您可以使用java.util.Date
类然后使用SimpleDateFormat
格式化Date
.
Date date=new Date(millis);
Run Code Online (Sandbox Code Playgroud)
我们可以使用java.time包(教程) - Java SE 8中引入的DateTime API.
var instance = java.time.Instant.ofEpochMilli(millis);
var localDateTime = java.time.LocalDateTime
.ofInstant(instance, java.time.ZoneId.of("Asia/Kolkata"));
var zonedDateTime = java.time.ZonedDateTime
.ofInstant(instance,java.time.ZoneId.of("Asia/Kolkata"));
Run Code Online (Sandbox Code Playgroud)
// Format the date
var formatter = java.time.format.DateTimeFormatter.ofPattern("u-M-d hh:mm:ss a O");
var string = zonedDateTime.format(formatter);
Run Code Online (Sandbox Code Playgroud)
Fai*_*raf 109
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(timeStamp);
int mYear = calendar.get(Calendar.YEAR);
int mMonth = calendar.get(Calendar.MONTH);
int mDay = calendar.get(Calendar.DAY_OF_MONTH);
Run Code Online (Sandbox Code Playgroud)
Bas*_*que 23
Instant.ofEpochMilli( 1_322_018_752_992L ) // Parse count of milliseconds-since-start-of-1970-UTC into an `Instant`.
.atZone( ZoneId.of( "Africa/Tunis" ) ) // Assign a time zone to the `Instant` to produce a `ZonedDateTime` object.
Run Code Online (Sandbox Code Playgroud)
其他答案使用过时或不正确的类.
避免使用旧的日期时间类,例如java.util.Date/.Calendar.事实证明,它们设计糟糕,令人困惑,并且很麻烦.
该java.time框架已内置到Java 8和更高版本.许多功能都被反向移植到Java 6和7,并进一步适应Android.由Joda-Time制作的一些人制作.
An Instant
是UTC时间轴上的一个时刻,分辨率为纳秒.它的时代是UTC的1970年的第一个时刻.
假设您的输入数据是1970-01-01T00:00:00Z(在问题中不清楚)的毫秒数,那么我们可以轻松地实例化一个Instant
.
Instant instant = Instant.ofEpochMilli( 1_322_018_752_992L );
Run Code Online (Sandbox Code Playgroud)
instant.toString():2011-11-23T03:25:52.992Z
在Z
该标准ISO 8601格式的字符串是短期的Zulu
,并指UTC.
使用适当的时区名称应用时区,以获得ZonedDateTime
.
ZoneId zoneId = ZoneId.of( "Asia/Kolkata" ) ;
ZonedDateTime zdt = instant.atZone( zoneId );
Run Code Online (Sandbox Code Playgroud)
请参阅IdeOne.com上的此代码.
Asia/Kolkata
时区 ?我猜你的印度时区正在影响你的代码.我们在这里看到,调整到Asia/Kolkata
时区会呈现与您报告时相同的时间,08:55
比我们的UTC值提前五个半小时03:25
.
2011-11-23T08:55:52.992 + 05:30 [亚/加尔各答]
您可以应用JVM 的当前默认时区.请注意,默认情况下可以在运行时期间随时更改.JVM中任何应用程序的任何线程中的任何代码都可以更改当前默认值.如果重要,请询问用户所需/预期的时区.
ZoneId zoneId = ZoneId.systemDefault();
ZonedDateTime zdt = ZonedDateTime.ofInstant( instant , zoneId );
Run Code Online (Sandbox Code Playgroud)
该java.time框架是建立在Java 8和更高版本.这些类取代麻烦的老传统日期时间类,如java.util.Date
,Calendar
,和SimpleDateFormat
.
现在处于维护模式的Joda-Time项目建议迁移到java.time类.
要了解更多信息,请参阅Oracle教程.并搜索Stack Overflow以获取许多示例和解释.规范是JSR 310.
使用符合JDBC 4.2或更高版本的JDBC驱动程序,您可以直接与数据库交换java.time对象.不需要字符串或java.sql.*类.
从哪里获取java.time类?
该ThreeTen-额外项目与其他类扩展java.time.该项目是未来可能添加到java.time的试验场.您可以在此比如找到一些有用的类Interval
,YearWeek
,YearQuarter
,和更多.
Bil*_*ill 13
如果millis值是自1970年1月1日GMT以来的毫秒数,这是JVM的标准,那么这与时区无关.如果要使用特定时区对其进行格式化,只需将其转换为GregorianCalendar对象并设置时区即可.之后,有很多方法可以格式化它.
Cam*_*ner 13
最简单的方法是使用Joda DateTime类并指定时间戳(以毫秒为单位)和所需的DateTimeZone.
我强烈建议避免使用内置的Java Date和Calendar类; 他们太可怕了.
Sid*_*ted 11
我的解决方案
public class CalendarUtils {
public static String dateFormat = "dd-MM-yyyy hh:mm";
private static SimpleDateFormat simpleDateFormat = new SimpleDateFormat(dateFormat);
public static String ConvertMilliSecondsToFormattedDate(String milliSeconds){
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(Long.parseLong(milliSeconds));
return simpleDateFormat.format(calendar.getTime());
}
}
Run Code Online (Sandbox Code Playgroud)
我是这样做的:
static String formatDate(long dateInMillis) {
Date date = new Date(dateInMillis);
return DateFormat.getDateInstance().format(date);
}
Run Code Online (Sandbox Code Playgroud)
您还可以使用getDateInstance(int style)
以下参数:
DateFormat.SHORT
DateFormat.MEDIUM
DateFormat.LONG
DateFormat.FULL
DateFormat.DEFAULT
SimpleDateFormat类有一个名为SetTimeZone(TimeZone)的方法,它继承自DateFormat类.http://docs.oracle.com/javase/6/docs/api/java/text/DateFormat.html
最简单的方法:
private String millisToDate(long millis){
return DateFormat.getDateInstance(DateFormat.SHORT).format(millis);
//You can use DateFormat.LONG instead of SHORT
}
Run Code Online (Sandbox Code Playgroud)