Question

J'ai une chaîne de date et je veux analyser à jour normale utiliser l'API Date de java, ce qui suit est mon code:

public static void main(String[] args) {
    String date="2010-10-02T12:23:23Z";
    String pattern="yyyy-MM-ddThh:mm:ssZ";
    SimpleDateFormat sdf=new SimpleDateFormat(pattern);
    try {
        Date d=sdf.parse(date);
        System.out.println(d.getYear());
    } catch (ParseException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
}

Cependant j'ai eu une exception: java.lang.IllegalArgumentException: Illegal pattern character 'T'

Je me demande si je dois diviser la chaîne et l'analyser manuellement?

BTW, j'ai essayé d'ajouter un caractère de guillemet simple de chaque côté du T:

String pattern="yyyy-MM-dd'T'hh:mm:ssZ";

Il ne fonctionne pas.

Était-ce utile?

La solution

Mise à jour pour Java 8 et plus

Vous pouvez simplement faire Instant.parse("2015-04-28T14:23:38.521Z") et obtenir la bonne chose maintenant, d'autant plus que vous devriez utiliser Instant au lieu du java.util.Date rompu avec les versions les plus récentes de Java.

Vous devez utiliser DateTimeFormatter au lieu de SimpleDateFormatter ainsi.

Réponse d'origine:

  

L'explication ci-dessous est toujours valide que ce que le format représente.   Mais il a été écrit avant que Java 8 était omniprésent il utilise l'ancien   les classes que vous ne devriez pas utiliser si vous utilisez Java ou 8   supérieur.

Cela fonctionne avec l'entrée avec le Z arrière comme l'a démontré:

  

Dans le motif du T se réfugiera avec ' de chaque côté.

     

Le motif de la Z à la fin est en fait XXX comme documenté   dans le JavaDoc pour SimpleDateFormat, il est tout simplement pas très clair   sur réellement comment l'utiliser depuis Z est le marqueur pour l'ancien   TimeZone renseignements.

Q2597083.java

import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Date;
import java.util.GregorianCalendar;
import java.util.TimeZone;

public class Q2597083
{
    /**
     * All Dates are normalized to UTC, it is up the client code to convert to the appropriate TimeZone.
     */
    public static final TimeZone UTC;

    /**
     * @see <a href="http://en.wikipedia.org/wiki/ISO_8601#Combined_date_and_time_representations">Combined Date and Time Representations</a>
     */
    public static final String ISO_8601_24H_FULL_FORMAT = "yyyy-MM-dd'T'HH:mm:ss.SSSXXX";

    /**
     * 0001-01-01T00:00:00.000Z
     */
    public static final Date BEGINNING_OF_TIME;

    /**
     * 292278994-08-17T07:12:55.807Z
     */
    public static final Date END_OF_TIME;

    static
    {
        UTC = TimeZone.getTimeZone("UTC");
        TimeZone.setDefault(UTC);
        final Calendar c = new GregorianCalendar(UTC);
        c.set(1, 0, 1, 0, 0, 0);
        c.set(Calendar.MILLISECOND, 0);
        BEGINNING_OF_TIME = c.getTime();
        c.setTime(new Date(Long.MAX_VALUE));
        END_OF_TIME = c.getTime();
    }

    public static void main(String[] args) throws Exception
    {

        final SimpleDateFormat sdf = new SimpleDateFormat(ISO_8601_24H_FULL_FORMAT);
        sdf.setTimeZone(UTC);
        System.out.println("sdf.format(BEGINNING_OF_TIME) = " + sdf.format(BEGINNING_OF_TIME));
        System.out.println("sdf.format(END_OF_TIME) = " + sdf.format(END_OF_TIME));
        System.out.println("sdf.format(new Date()) = " + sdf.format(new Date()));
        System.out.println("sdf.parse(\"2015-04-28T14:23:38.521Z\") = " + sdf.parse("2015-04-28T14:23:38.521Z"));
        System.out.println("sdf.parse(\"0001-01-01T00:00:00.000Z\") = " + sdf.parse("0001-01-01T00:00:00.000Z"));
        System.out.println("sdf.parse(\"292278994-08-17T07:12:55.807Z\") = " + sdf.parse("292278994-08-17T07:12:55.807Z"));
    }
}

produit la sortie suivante:

sdf.format(BEGINNING_OF_TIME) = 0001-01-01T00:00:00.000Z
sdf.format(END_OF_TIME) = 292278994-08-17T07:12:55.807Z
sdf.format(new Date()) = 2015-04-28T14:38:25.956Z
sdf.parse("2015-04-28T14:23:38.521Z") = Tue Apr 28 14:23:38 UTC 2015
sdf.parse("0001-01-01T00:00:00.000Z") = Sat Jan 01 00:00:00 UTC 1
sdf.parse("292278994-08-17T07:12:55.807Z") = Sun Aug 17 07:12:55 UTC 292278994

Autres conseils

tl; dr

Instant.parse( "2010-10-02T12:23:23Z" )

ISO 8601

Ce format est défini par les ISO 8601 standard pour les formats de chaîne date-heure.

Les deux:

... utiliser des formats ISO 8601 par défaut pour parser et générer des chaînes.

Vous devez généralement évitez d'utiliser l'ancien java.util.Date /. Calendrier et cours java.text.SimpleDateFormat comme ils sont notoirement gênants, confus et imparfait. Si nécessaire pour interopérer, vous pouvez convertir çà et là.

java.time

Construit en Java 8 et est plus tard, le nouveau Joda-Time , défini par JSR 310 et prolongée par le ThreeTen-extra projet .

Instant instant = Instant.parse( "2010-10-02T12:23:23Z" );  // `Instant` is always in UTC.

Convertir à l'ancienne classe.

java.util.Date date = java.util.Date.from( instant );  // Pass an `Instant` to the `from` method.

Fuseau horaire

Si nécessaire, vous pouvez attribuer un fuseau horaire.

ZoneId zoneId = ZoneId.of( "America/Montreal" ); // Define a time zone rather than rely implicitly on JVM’s current default time zone.
ZonedDateTime zdt = ZonedDateTime.ofInstant( instant , zoneId );  // Assign a time zone adjustment from UTC.

Convert.

java.util.Date date = java.util.Date.from( zdt.toInstant() );  // Extract an `Instant` from the `ZonedDateTime` to pass to the `from` method.

Joda-Time

MISE À JOUR: Le projet Joda-Time est maintenant en mode maintenance. L'équipe conseille la migration vers java.time classes.

Voici quelques exemples de code dans Joda-Time 2.8.

org.joda.time.DateTime dateTime_Utc = new DateTime( "2010-10-02T12:23:23Z" , DateTimeZone.UTC );  // Specifying a time zone to apply, rather than implicitly assigning the JVM’s current default.

Convertir en ancienne classe. Notez que le fuseau horaire attribué est perdu dans la conversion, comme j.u.Date ne peut être attribué un fuseau horaire.

java.util.Date date = dateTime_Utc.toDate(); // The `toDate` method converts to old class.

Fuseau horaire

Si nécessaire, vous pouvez attribuer un fuseau horaire.

DateTimeZone zone = DateTimeZone.forID( "America/Montreal" );
DateTime dateTime_Montreal = dateTime_Utc.withZone ( zone );

A propos de java.time

Le java.time cadre est construit en Java 8 et versions ultérieures. Ces classes supplantent les href="https://en.wikipedia.org/wiki/Legacy_system" gênants vieux les classes date-heure comme java.util.Date , Calendar , et SimpleDateFormat .

Le Joda-Time projet , maintenant < a href = "https://en.wikipedia.org/wiki/Maintenance_mode" rel = "nofollow noreferrer"> mode maintenance , conseille la migration vers la page noreferrer java.time classes .

Pour en savoir plus, consultez le Oracle Tutorial . Et la recherche Stack Overflow pour de nombreux exemples et explications. Spécification est JSR 310 .

Vous pouvez échanger des java.time objets directement avec votre base de données. Utilisez un pilote JDBC conforme JDBC 4.2 ou later. Pas besoin de chaînes, pas besoin de classes java.sql.*.

Où obtenir les classes java.time?

Le projet ThreeTen-Extra étend java.time avec des classes supplémentaires. Ce projet est un terrain d'essai pour les futurs ajouts possibles à java.time. Vous trouverez peut-être des classes utiles ici, comme Interval , YearWeek , YearQuarter et plus .

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top