IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Langage Java Discussion :

Récupérer le format d'une date à partir d'un String


Sujet :

Langage Java

  1. #1
    Membre du Club
    Femme Profil pro
    Étudiant
    Inscrit en
    Octobre 2012
    Messages
    50
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Octobre 2012
    Messages : 50
    Points : 52
    Points
    52
    Par défaut Récupérer le format d'une date à partir d'un String
    Bonjour à tous,

    Je suis en train de me casser la tête pour parser une date d'un format à un autre.

    Petite explication :
    - J'ai un string en entrée qui correspond à une date (jusque là convertir un String en Date je sais faire). SAUF que ce String peut être de n'importe quel format : "08012018" ou bien "080118" ou bien "08/01/18"... etc.
    - Je voudrais récupérer le format de la string/date. Exemple : Si ma string en Entrée est "08012018" je voudrais retrouver "ddMMyyyy".
    - Je convertis (avec SimpleDateFormat) à partir du format source (ici ddMMyyyy) vers le format cible ("dd/MM/yyyy") vu que je connais maintenant le format (donc pas d'erreur Unparsable normalement).

    Sauf qu'à part faire des if/else ou try/catch pour essayer de parser avec tous les formats possibles, je ne vois pas comment faire pour réaliser l'étape 2 proprement...

    Est-ce que vous avez une idée svp ?

    Merci beaucoup

  2. #2
    Membre expert

    Homme Profil pro
    Consultant informatique
    Inscrit en
    Janvier 2004
    Messages
    2 301
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Suisse

    Informations professionnelles :
    Activité : Consultant informatique
    Secteur : Finance

    Informations forums :
    Inscription : Janvier 2004
    Messages : 2 301
    Points : 3 675
    Points
    3 675
    Par défaut
    Une idée, ouais: c'est impossible à faire de façon "sûre"

    Vas-y, retrouve le jour mois année heure minute seconde là: 010101 010101C'est pour ça qu'on se met d'accord sur les formats AVANT en général

    "Le plug gros problème des citations trouvées sur internet, c'est qu'on ne peut jamais garantir leur authenticité"

    Confucius, 448 av. J-C

  3. #3
    Modérateur
    Avatar de joel.drigo
    Homme Profil pro
    Ingénieur R&D - Développeur Java
    Inscrit en
    Septembre 2009
    Messages
    12 430
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 54
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Ingénieur R&D - Développeur Java
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2009
    Messages : 12 430
    Points : 29 131
    Points
    29 131
    Billets dans le blog
    2
    Par défaut
    Salut,

    Le premier souci, c'est le "etc" dans ta question. C'est quoi les autres formats possibles ? Parce que comme dit @Pill_s, on peut obtenir de nombreux cas qui matchent plusieurs formats éventuellement. Si c'est pour une reprise de données, ça peut se comprendre, sinon, c'est plutôt à éviter. Surtout l'année sur 2 chiffres : on l'a assez payé au passage à l'an 2000, on va pas repartir sur la même idée bancale pour économiser 2 caractères !

    Au passage, plutôt utiliser java.time, que java.util.Date et consort.



    1. Sur la base des 3 formats que tu cites, à savoir "ddMMyyyy", "ddMMyy", et "dd/MM/yyyy", on peut faire des tests avant de déterminer quel format utiliser. On peut par exemple procéder d'abord par une expression régulière. Donc des expressions du type \d{8}, \d{6} et \d{2}/\d{2}/\d{4} pour commencer.
      Exemple :
      Code : Sélectionner tout - Visualiser dans une fenêtre à part
      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      if ( stringDate.matches("\\d{8}") ) {
         // j'utilise le format "ddMMyyyy"
      }
      else if ( stringDate.matches("\\d{6}") ) {
         // j'utilise le format "ddMMyy"
      }
      else if ( stringDate.matches("\\d{1,2}/\\d{1,2}/\\d{2}") ) {
         // j'utilise le format d/M/yy
      }
      else if ( stringDate.matches("\\d{1,2}/\\d{1,2}/\\d{4}") ) {
         // j'utilise le format d/M/yyyy
      }
      /* etc */
      Ensuite, première extension possible, changer le séparateur, qu'on peut faire par un "replace" par exemple, pour se retrouver forcément avec une chaîne compatible avec

      Autre possibilité, tester le nombre de caractères (if ( stringDate.length()<=6 ) ...)

      En revanche, il te faudra tout de même faire des try/catch, sauf refaire tous les tests pour la validation des valeurs (le mois doit être entre 1 et 12, le nombre de jours dépend du mois, etc).

    2. Note qu'on peut avoir certains formats hybrides avec les DateTimeFormatter. Mais je ne crois pas qu'on puisse en faire qui traitent les trois cas en un format. Le souci est qu'on ne peut gérer à la fois le cas sans séparateur et le cas avec, si la longueur d'un champ n'est pas fixée, forcément (parce que le parsing ne traite que des chaînes en premier lieu).

      Par exemple, DateTimeFormatter.ofPattern("dd['/']MM['/']yyyy") permet de parser 01022018 et 01/02/2018 mais pas 1/2/2018 en revanche, alors que DateTimeFormatter.ofPattern("d/M/yyyy") parse 1/2/2018 et 01/02/2018 mais pas 01022018.


    3. On pourrait envisage également d'étendre la notion de prétraitement afin de convertir toute chaîne afin de la rendre compatible avec un unique format de date. Cela fait quelques manipulations de chaînes, mais évite de se trimbaler 36 formats de date pour tous les essayer (le throw/catch c'est coûteux, possiblement plus au final que quelques tests et quelques append sur un StringBuilder bien dimensionné au départ.
    L'expression "ça marche pas" ne veut rien dire. Indiquez l'erreur, et/ou les comportements attendus et obtenus, et donnez un Exemple Complet Minimal qui permet de reproduire le problème.
    La plupart des réponses à vos questions sont déjà dans les FAQs ou les Tutoriels, ou peut-être dans une autre discussion : utilisez la recherche interne.
    Des questions sur Java : consultez le Forum Java. Des questions sur l'EDI Eclipse ou la plateforme Eclipse RCP : consultez le Forum Eclipse.
    Une question correctement posée et rédigée et vous aurez plus de chances de réponses adaptées et rapides.
    N'oubliez pas de mettre vos extraits de code entre balises CODE (Voir Mode d'emploi de l'éditeur de messages).
    Nouveau sur le forum ? Consultez Les Règles du Club.

  4. #4
    Membre expert

    Homme Profil pro
    Consultant informatique
    Inscrit en
    Janvier 2004
    Messages
    2 301
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Suisse

    Informations professionnelles :
    Activité : Consultant informatique
    Secteur : Finance

    Informations forums :
    Inscription : Janvier 2004
    Messages : 2 301
    Points : 3 675
    Points
    3 675
    Par défaut
    Pour limiter les cas de formats à parser, on pourrait aussi commencer par enlever les slashs, les points, etc. quand ils n'apportent rien

    Mais c'est vraiment foireux, perso je mettrais plutôt l'accent sur la définition stricte des formats plutôt que sur un parsing adaptatif. Je préfère prendre une ParseException que de risquer un parsing incorrect...
    "Le plug gros problème des citations trouvées sur internet, c'est qu'on ne peut jamais garantir leur authenticité"

    Confucius, 448 av. J-C

  5. #5
    Modérateur
    Avatar de joel.drigo
    Homme Profil pro
    Ingénieur R&D - Développeur Java
    Inscrit en
    Septembre 2009
    Messages
    12 430
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 54
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Ingénieur R&D - Développeur Java
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2009
    Messages : 12 430
    Points : 29 131
    Points
    29 131
    Billets dans le blog
    2
    Par défaut
    Citation Envoyé par Pill_S Voir le message
    Pour limiter les cas de formats à parser, on pourrait aussi commencer par enlever les slashs, les points, etc. quand ils n'apportent rien
    Le souci avec cette solution, c'est que si on a "11/2/2018" ou "1/12/2018" en entrée, on se retrouve avec "1122018" dans les deux cas, et c'est mort, ou alors il faut faire un padding avec des 0 avant.
    Bref, on est d'accord, un format fixe déterminé à l'avance (genre du ISO en ce qui me concerne pour du fichier produit automatiquement et un format par style pour de la saisie "humaine"), c'est beaucoup moins de souci sur la fiabilité des données. Surtout avec les petits malins qui te saisissent du "le 1 02 94 entre 10 et 12 (ou éventuellement 18h si pas possible le matin)" comme j'ai vu dans une base pure texte que j'avais dû reprendre pour injecter dans du Sybase y'a longtemps )
    L'expression "ça marche pas" ne veut rien dire. Indiquez l'erreur, et/ou les comportements attendus et obtenus, et donnez un Exemple Complet Minimal qui permet de reproduire le problème.
    La plupart des réponses à vos questions sont déjà dans les FAQs ou les Tutoriels, ou peut-être dans une autre discussion : utilisez la recherche interne.
    Des questions sur Java : consultez le Forum Java. Des questions sur l'EDI Eclipse ou la plateforme Eclipse RCP : consultez le Forum Eclipse.
    Une question correctement posée et rédigée et vous aurez plus de chances de réponses adaptées et rapides.
    N'oubliez pas de mettre vos extraits de code entre balises CODE (Voir Mode d'emploi de l'éditeur de messages).
    Nouveau sur le forum ? Consultez Les Règles du Club.

  6. #6
    Expert éminent sénior
    Avatar de tchize_
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Avril 2007
    Messages
    25 481
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 44
    Localisation : Belgique

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2007
    Messages : 25 481
    Points : 48 806
    Points
    48 806
    Par défaut
    Personellement quand je dois travailler avec un fichier qui contient plusieurs formats historiques, si ça dépasse 2 cas, j'ai tendance à me faire si possible une LinkedHashMap<Pattern,Parser> dans laquelle la clé est une pattern et le Parser forme les règles à utiliser si ça match (ici, ton SimpleDateFormat).
    Ensuite, pour chaque donnée brute, je parcours la map jusqu'à matcher une Pattern et j'applique le Parser.

Discussions similaires

  1. [Toutes versions] Récupérer une date à partir des valeurs de 3 ComboBox
    Par ch0ubida dans le forum Macros et VBA Excel
    Réponses: 10
    Dernier message: 03/12/2014, 11h48
  2. [2008R2] Récupérer une date à partir d'un numéro de semaine et d'une année.
    Par ff.martin dans le forum Développement
    Réponses: 5
    Dernier message: 24/07/2014, 15h20
  3. Réponses: 2
    Dernier message: 17/04/2012, 16h34
  4. [XL-2003] Récupérer une date à partir du numéro de semaine
    Par tarnx dans le forum Macros et VBA Excel
    Réponses: 3
    Dernier message: 29/03/2011, 00h32
  5. Récupérer une date à partir d'un format UNIX
    Par Spack dans le forum Programmation et administration système
    Réponses: 8
    Dernier message: 09/02/2009, 14h46

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo