tl; dr
myUtilDate.toInstant() // Convert `java.util.Date` to `Instant`.
.atOffset( ZoneOffset.UTC ) // Transform `Instant` to `OffsetDateTime`.
.format( DateTimeFormatter.ISO_LOCAL_DATE_TIME ) // Generate a String.
.replace( "T" , " " ) // Put a SPACE in the middle.
2014-11-14 14:05:09
java.time
La forma moderna es con las clases java.time que ahora suplantan a las antiguas clases problemáticas de fecha y hora heredadas.
Primero convierta su java.util.Date
a un Instant
. La Instant
clase representa un momento en la línea de tiempo en UTC con una resolución de nanosegundos (hasta nueve (9) dígitos de una fracción decimal).
Las conversiones hacia / desde java.time se realizan mediante nuevos métodos agregados a las clases antiguas.
Instant instant = myUtilDate.toInstant();
Tanto tu java.util.Date
como java.time.Instant
estás en UTC . Si desea ver la fecha y la hora como UTC, que así sea. Llame toString
para generar una cadena en formato estándar ISO 8601 .
String output = instant.toString();
2014-11-14T14: 05: 09Z
Para otros formatos, debe transformar su Instant
en el más flexible OffsetDateTime
.
OffsetDateTime odt = instant.atOffset( ZoneOffset.UTC );
odt.toString (): 2020-05-01T21: 25: 35.957Z
Vea ese código en vivo en IdeOne.com .
Para obtener una cadena en el formato deseado, especifique a DateTimeFormatter
. Puede especificar un formato personalizado. Pero usaría uno de los formateadores predefinidos ( ISO_LOCAL_DATE_TIME
) y reemplazaría el T
en su salida con un ESPACIO.
String output = odt.format( DateTimeFormatter.ISO_LOCAL_DATE_TIME )
.replace( "T" , " " );
2014-11-14 14:05:09
Por cierto, no recomiendo este tipo de formato en el que pierdes intencionalmente la información de compensación de UTC o zona horaria. Crea ambigüedad en cuanto al significado del valor de fecha y hora de esa cadena.
También tenga cuidado con la pérdida de datos, ya que cualquier segundo fraccionario se ignora (se trunca efectivamente) en la representación de su Cadena del valor de fecha y hora.
Para ver ese mismo momento a través de la lente del reloj de pared de una región en particular , aplique a ZoneId
para obtener a ZonedDateTime
.
ZoneId z = ZoneId.of( "America/Montreal" );
ZonedDateTime zdt = instant.atZone( z );
zdt.toString (): 2014-11-14T14: 05: 09-05: 00 [América / Montreal]
Para generar una cadena formateada, haga lo mismo que arriba pero reemplace odt
con zdt
.
String output = zdt.format( DateTimeFormatter.ISO_LOCAL_DATE_TIME )
.replace( "T" , " " );
2014-11-14 14:05:09
Si ejecuta este código una gran cantidad de veces, es posible que desee ser un poco más eficiente y evitar la llamada String::replace
. Descartar esa llamada también hace que su código sea más corto. Si lo desea, especifique su propio patrón de formato en su propio DateTimeFormatter
objeto. Caché esta instancia como una constante o miembro para su reutilización.
DateTimeFormatter f = DateTimeFormatter.ofPattern( "uuuu-MM-dd HH:mm:ss" ); // Data-loss: Dropping any fractional second.
Aplique ese formateador pasando la instancia.
String output = zdt.format( f );
Sobre java.time
El marco java.time está integrado en Java 8 y versiones posteriores. Estas clases sustituyen a las clases de fecha y hora viejas problemáticas tales como java.util.Date
, .Calendar
, y java.text.SimpleDateFormat
.
El proyecto Joda-Time , ahora en modo de mantenimiento , aconseja la migración a java.time.
Para obtener más información, vea el Tutorial de Oracle . Y busque Stack Overflow para obtener muchos ejemplos y explicaciones.
Gran parte de la funcionalidad java.time se transfiere a Java 6 y 7 en ThreeTen-Backport y se adapta aún más a Android en ThreeTenABP (consulte Cómo usar ... ).
El proyecto ThreeTen-Extra extiende java.time con clases adicionales. Este proyecto es un campo de pruebas para posibles adiciones futuras a java.time.