Преобразование даты Java в строку UTC
на java.утиль.Дата toString()
метод отображает дату в местном часовом поясе.
существует несколько распространенных сценариев, в которых мы хотим, чтобы данные были напечатаны в UTC, включая журналы, экспорт данных и связь с внешними программами.
- каков наилучший способ создания строкового представления
java.util.Date
в UTC? - как заменить j.u.Дата
toString()
формат, который не сортируется (спасибо, @JonSkeet!) с лучшим форматом?
дополнительное соглашение
Я думаю, что стандартный способ печати даты в пользовательском формате и часовом поясе довольно утомительно:
final Date date = new Date();
final String ISO_FORMAT = "yyyy-MM-dd'T'HH:mm:ss.SSS zzz";
final SimpleDateFormat sdf = new SimpleDateFormat(ISO_FORMAT);
final TimeZone utc = TimeZone.getTimeZone("UTC");
sdf.setTimeZone(utc);
System.out.println(sdf.format(date));
Я искал один-лайнер, как:
System.out.println(prettyPrint(date, "yyyy-MM-dd'T'HH:mm:ss.SSS zzz", "UTC"));
7 ответов
java.время
в Java 8 и позже у нас есть новый java.пакет времени построен в (учебник). Вдохновленный Joda-Time, определенный JSR 310 и расширенный ThreeTen-Extra.
лучшее решение -сортировать объекты даты и времени, а не строки. Но если вы должны работать в строках, читайте дальше.
An Instant
представляет момент на временной шкале, в основном в UTC (см. class doc для точных деталей). The toString
реализация использует DateTimeFormatter.ISO_INSTANT
формат по умолчанию. Этот формат включает ноль, три, шесть или девять цифр цифр, необходимых для отображения доли секунды до НС точности.
String output = Instant.now().toString(); // Example: '2015-12-03T10:15:30.120Z'
если вы должны взаимодействовать со старых Date
класс, преобразовать в / из java.время с помощью новых методов, добавленных к старым классам. Образец: Date::toInstant
.
myJavaUtilDate.toInstant().toString()
вы можете использовать альтернативный форматер, если вам нужно согласованное количество цифр в дробной секунде или если вам не нужна дробная секунда.
другой маршрут, если вы хотите усечь доли секунды, это использовать ZonedDateTime
вместо Instant
, назвав его метод изменения дроби на ноль.
обратите внимание, что мы должны указать часовой пояс ZonedDateTime
(отсюда и название). В нашем случае это означает UTC. Этот подкласс ZoneID
, ZoneOffset
, имеет удобный константа для UTC. Если мы опустим часовой пояс, JVM текущий часовой пояс неявно применяется.
String output = ZonedDateTime.now( ZoneOffset.UTC ).withNano( 0 ).toString(); // Example: 2015-08-27T19:28:58Z
Joda Времени
обновление: проект Joda-Time теперь находится в режиме обслуживания, с командой, консультирующей миграцию на java.классы время.
я искал одну строчку
легко при использовании Joda Времени 2.3 библиотека. ISO 8601 форматирование по умолчанию.
Часовой Пояс
в приведенном ниже примере кода обратите внимание, что я указываю часовой пояс, а не в зависимости от часового пояса по умолчанию. В этом случае я указываю UTC на ваш вопрос. The Z
в конце, говорят как "Зулу", означает отсутствие смещения часового пояса от UTC.
пример Код
// import org.joda.time.*;
String output = new DateTime( DateTimeZone.UTC );
выход...
2013-12-12T18:29:50.588Z
следуя полезным комментариям, я полностью перестроил форматер даты. Использование должно:
- быть коротким (один вкладыш)
- представлять одноразовые объекты (часовой пояс, формат) в виде строк
- поддержка полезных, сортируемых форматов ISO и устаревшего формата из коробки
Если вы считаете этот код полезным, я могу опубликовать источник и банку в на GitHub.
использование
// The problem - not UTC
Date.toString()
"Tue Jul 03 14:54:24 IDT 2012"
// ISO format, now
PrettyDate.now()
"2012-07-03T11:54:24.256 UTC"
// ISO format, specific date
PrettyDate.toString(new Date())
"2012-07-03T11:54:24.256 UTC"
// Legacy format, specific date
PrettyDate.toLegacyString(new Date())
"Tue Jul 03 11:54:24 UTC 2012"
// ISO, specific date and time zone
PrettyDate.toString(moonLandingDate, "yyyy-MM-dd hh:mm:ss zzz", "CST")
"1969-07-20 03:17:40 CDT"
// Specific format and date
PrettyDate.toString(moonLandingDate, "yyyy-MM-dd")
"1969-07-20"
// ISO, specific date
PrettyDate.toString(moonLandingDate)
"1969-07-20T20:17:40.234 UTC"
// Legacy, specific date
PrettyDate.toLegacyString(moonLandingDate)
"Wed Jul 20 08:17:40 UTC 1969"
код
(этот код также является предметом вопрос по обзору кода stackexchange)
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.TimeZone;
/**
* Formats dates to sortable UTC strings in compliance with ISO-8601.
*
* @author Adam Matan <adam@matan.name>
* @see http://stackoverflow.com/questions/11294307/convert-java-date-to-utc-string/11294308
*/
public class PrettyDate {
public static String ISO_FORMAT = "yyyy-MM-dd'T'HH:mm:ss.SSS zzz";
public static String LEGACY_FORMAT = "EEE MMM dd hh:mm:ss zzz yyyy";
private static final TimeZone utc = TimeZone.getTimeZone("UTC");
private static final SimpleDateFormat legacyFormatter = new SimpleDateFormat(LEGACY_FORMAT);
private static final SimpleDateFormat isoFormatter = new SimpleDateFormat(ISO_FORMAT);
static {
legacyFormatter.setTimeZone(utc);
isoFormatter.setTimeZone(utc);
}
/**
* Formats the current time in a sortable ISO-8601 UTC format.
*
* @return Current time in ISO-8601 format, e.g. :
* "2012-07-03T07:59:09.206 UTC"
*/
public static String now() {
return PrettyDate.toString(new Date());
}
/**
* Formats a given date in a sortable ISO-8601 UTC format.
*
* <pre>
* <code>
* final Calendar moonLandingCalendar = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
* moonLandingCalendar.set(1969, 7, 20, 20, 18, 0);
* final Date moonLandingDate = moonLandingCalendar.getTime();
* System.out.println("UTCDate.toString moon: " + PrettyDate.toString(moonLandingDate));
* >>> UTCDate.toString moon: 1969-08-20T20:18:00.209 UTC
* </code>
* </pre>
*
* @param date
* Valid Date object.
* @return The given date in ISO-8601 format.
*
*/
public static String toString(final Date date) {
return isoFormatter.format(date);
}
/**
* Formats a given date in the standard Java Date.toString(), using UTC
* instead of locale time zone.
*
* <pre>
* <code>
* System.out.println(UTCDate.toLegacyString(new Date()));
* >>> "Tue Jul 03 07:33:57 UTC 2012"
* </code>
* </pre>
*
* @param date
* Valid Date object.
* @return The given date in Legacy Date.toString() format, e.g.
* "Tue Jul 03 09:34:17 IDT 2012"
*/
public static String toLegacyString(final Date date) {
return legacyFormatter.format(date);
}
/**
* Formats a date in any given format at UTC.
*
* <pre>
* <code>
* final Calendar moonLandingCalendar = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
* moonLandingCalendar.set(1969, 7, 20, 20, 17, 40);
* final Date moonLandingDate = moonLandingCalendar.getTime();
* PrettyDate.toString(moonLandingDate, "yyyy-MM-dd")
* >>> "1969-08-20"
* </code>
* </pre>
*
*
* @param date
* Valid Date object.
* @param format
* String representation of the format, e.g. "yyyy-MM-dd"
* @return The given date formatted in the given format.
*/
public static String toString(final Date date, final String format) {
return toString(date, format, "UTC");
}
/**
* Formats a date at any given format String, at any given Timezone String.
*
*
* @param date
* Valid Date object
* @param format
* String representation of the format, e.g. "yyyy-MM-dd HH:mm"
* @param timezone
* String representation of the time zone, e.g. "CST"
* @return The formatted date in the given time zone.
*/
public static String toString(final Date date, final String format, final String timezone) {
final TimeZone tz = TimeZone.getTimeZone(timezone);
final SimpleDateFormat formatter = new SimpleDateFormat(format);
formatter.setTimeZone(tz);
return formatter.format(date);
}
}
следующий упрощенный код, основанный на принятый ответ выше, работал на меня:
public class GetSync {
public static String ISO_FORMAT = "yyyy-MM-dd'T'HH:mm:ss.SSS zzz";
private static final TimeZone utc = TimeZone.getTimeZone("UTC");
private static final SimpleDateFormat isoFormatter = new SimpleDateFormat(ISO_FORMAT);
static {
isoFormatter.setTimeZone(utc);
}
public static String now() {
return isoFormatter.format(new Date()).toString();
}
}
надеюсь, это кому-то поможет.
java.время.Instant
просто использовать Instant
of java.time
.
System.out.println(Instant.now());
это только что напечатано:
2018-01-27T09:35:23.179612Z
Instant.toString
всегда дает время UTC.
выход обычно сортируется, но есть неудачные исключения. toString
дает вам достаточно групп из трех десятичных знаков, чтобы отобразить точность, которую он держит. На Java 9 на моем Mac точность Instant.now()
кажется, микросекунды, но мы должны ожидать что примерно в одном случае из тысячи он попадет в целое число миллисекунд и напечатает только три десятичных знака. Строки с неравным числом десятичных знаков будут отсортированы в неправильном порядке (если вы не напишете пользовательский компаратор для учета этого).
Instant
один из классов в java.time
, современный API даты и времени Java, который я настоятельно рекомендую использовать вместо устаревшего Date
класса. java.time
встроен в Java 8 и позже, а также был backported на Java 6 и 7.
Если XStream является зависимостью, попробуйте:
new com.thoughtworks.xstream.converters.basic.DateConverter().toString(date)
почему бы просто не использовать Java.текст.Класса simpledateformat ?
Date someDate = new Date();
SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd");
String s = df.format(someDate);
или увидеть: http://www.tutorialspoint.com/java/java_date_time.htm
Ну, если вы хотите использовать Java.утиль.Только дата, вот небольшой трюк, который вы можете использовать:
строка dateString = Long.метод toString(дата.UTC(дата.getYear (), дата.getMonth(), дата.getDate (), дата.getHours(), дата.getMinutes(), дата.getSeconds()));