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

avec Java Discussion :

[Sérialisation] Différence entre deux méthodes


Sujet :

avec Java

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Inactif   Avatar de Deallyra
    Profil pro
    Étudiant
    Inscrit en
    Février 2007
    Messages
    1 997
    Détails du profil
    Informations personnelles :
    Âge : 37
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Février 2007
    Messages : 1 997
    Par défaut [Sérialisation] Différence entre deux méthodes
    Bonjour,

    Voici deux méthodes que j'ai utilisé dans des projets sans chercher réellement à savoir ce qu'elles faisaient.

    Code Java : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
     
        /**
         * @param T t Un objet à sérialiser
         * @param String fichierSortie le fichier dans lequel devra être sérialiser l'objet
         * @return <T> void
         */
        public <T> void serializer(T t, String fichierSortie){
            try {
                // ouverture d'un flux de sortie vers le fichier nomObjet.serial
                FileOutputStream fos = new FileOutputStream(fichierSortie + ".serial");
     
                // création d'un "flux objet" avec le flux fichier
                ObjectOutputStream oos= new ObjectOutputStream(fos);
                try {
                    // sérialisation : écriture de l'objet dans le flux de sortie
                    oos.writeObject(t);
                    // on vide le tampon
                    oos.flush();
                    System.out.println(t + " a ete serialise");
                } finally {
                    //fermeture des flux
                    try {
                        oos.close();
                    } finally {
                        fos.close();
                    }
                }
            }

    Code Java : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
     
    	public <T> void writeFile(T t, String fichierSortie) throws IOException {
    		ObjectOutput out = null;
    		try {
    			out = new ObjectOutputStream(new FileOutputStream(fichierSortie + ".serial"));
    			out.writeObject(t);
    		} finally {
    			out.close();
    		}
    	}

    Quelle est la méthode à utiliser ?
    Laquelle est la plus... fiable ou mieux écrite ?

    Quelles sont les différences entre ces deux méthodes ?

    Merci à vous,
    *Si la réponse vous convient, n'oubliez pas le tag
    *Exprimez vous dans un français correct; on prend le temps de vous lire, prenez le temps de bien écrire.
    *Et comment on interprète votre code? N'oubliez pas la balise!

    *Pour une mise en page simple avec des divs.
    *Pour faire des formulaires xHTML CSS.

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

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

    Informations forums :
    Inscription : Avril 2007
    Messages : 25 482
    Par défaut
    la deuxième est la plus courte et est, techinquement, la même. Note qu'il n'est pas nécessaire de fermer les deux flux, car la fermeture de l'objectoutputstream ferme l'outputstream.

    Note, je sais pas que quel type est T mais ce serait bien de le contraindre au "Serializable" :p

  3. #3
    Inactif   Avatar de Deallyra
    Profil pro
    Étudiant
    Inscrit en
    Février 2007
    Messages
    1 997
    Détails du profil
    Informations personnelles :
    Âge : 37
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Février 2007
    Messages : 1 997
    Par défaut
    Le contraindre ?

    Par un implements Serializable ?
    *Si la réponse vous convient, n'oubliez pas le tag
    *Exprimez vous dans un français correct; on prend le temps de vous lire, prenez le temps de bien écrire.
    *Et comment on interprète votre code? N'oubliez pas la balise!

    *Pour une mise en page simple avec des divs.
    *Pour faire des formulaires xHTML CSS.

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

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

    Informations forums :
    Inscription : Avril 2007
    Messages : 25 482
    Par défaut
    oui, de toutes façons, objectoutputstream envoie des exception sur les non-serializables

  5. #5
    Inactif   Avatar de Deallyra
    Profil pro
    Étudiant
    Inscrit en
    Février 2007
    Messages
    1 997
    Détails du profil
    Informations personnelles :
    Âge : 37
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Février 2007
    Messages : 1 997
    Par défaut
    Parlant d'exception, j'aimerai tester si je peux désérialiser un fichier.

    Pour ce faire, j'avais pensé à :
    Code Java : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
     
            //Création d'un IOData
                IOData iodata = new IOData();
     
            /* On s'occupe des Avions */
            ArrayList<Avion> desAvions = null;
            try {
                iodata.deserializer(desAvions, "avion");
                System.out.println("Not in the pocket but in the try");
            }
        	catch (NullPointerException e) {
                Avion a1 = new Avion("Airbus A340-300", 295, 129300, 55600, 10000, 13000, 140640,140640);
                desAvions.add(a1);
                System.out.println("In the pocket but not in the try T_T");
            }

    En fait, je pensais que si le fichier n'existait pas, il irait me lever une exception puis entrerait dans le catch...
    Mais cela ne semble pas être le cas puisque
    java.io.FileNotFoundException: avion.serial (Le fichier spécifié est introuvable)
    Not in the pocket but in the try
    at java.io.FileInputStream.open(Native Method)
    at java.io.FileInputStream.<init>(FileInputStream.java:106)
    at java.io.FileInputStream.<init>(FileInputStream.java:66)
    at trafficaerien.IOData.deserializer(IOData.java:71)
    at trafficaerien.Main.main(Main.java:32)
    (...)
    et lorsque le fichier existe :
    Airbus A340-300 a ete deserialise
    Not in the pocket but in the try
    (...)
    *Si la réponse vous convient, n'oubliez pas le tag
    *Exprimez vous dans un français correct; on prend le temps de vous lire, prenez le temps de bien écrire.
    *Et comment on interprète votre code? N'oubliez pas la balise!

    *Pour une mise en page simple avec des divs.
    *Pour faire des formulaires xHTML CSS.

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

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

    Informations forums :
    Inscription : Avril 2007
    Messages : 25 482
    Par défaut
    Citation Envoyé par Deallyra Voir le message
    En fait, je pensais que si le fichier n'existait pas, il irait me lever une exception puis entrerait dans le catch...
    Mais cela ne semble pas être le cas
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    java.io.FileNotFoundException: avion.serial (Le fichier spécifié est introuvable)
    En ce qui me concerne, ca semble bien être une exception ça

  7. #7
    Expert éminent
    Avatar de adiGuba
    Homme Profil pro
    Développeur Java/Web
    Inscrit en
    Avril 2002
    Messages
    13 938
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Java/Web
    Secteur : Transports

    Informations forums :
    Inscription : Avril 2002
    Messages : 13 938
    Billets dans le blog
    1
    Par défaut
    Salut,

    Citation Envoyé par tchize_ Voir le message
    la deuxième est la plus courte et est, techinquement, la même.
    Les deux sont problèmatique

    Dans le premier cas si tu as une exception lors de la création de l'ObjectOutputStream tu ne fermes aucun fichier car on n'est pas encore entré dans le try/finally, et tu conserves donc un fichier ouvert
    Il faut obligatoirement utiliser un try/finally par flux, avec uniquement un seul close() par finally.


    Dans le second cas tu ouvres le fichier alors que tu es déjà dans le try/finally, et en cas d'erreurs d'ouverture du fichier tu auras un NullPointerException
    C'est problématique car ce NullPointerException va te cacher l'exception survenu lors de l'ouverture du fichier, et donc la réelle cause du problème.


    Comme indiqué dans la FAQ, il faut utiliser un code comme celui-ci :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
     
    Flux res = new ...
    try {
       // traitements...
    } finally {
       res.close();
    }
    (note : ce code n'est pas encore parfait, puisque le close() peut générer une exception qui cacherait une autre exception survenir dans le try, mais c'est toutefois un cas assez rare et cela nécessite aussi des traitements plus important).


    Toutefois si dans 99% des cas on peut empiler les appels, on ne peut pas le faire avec les Object*Stream car leurs constructeurs peuvent générer des exception. Concrètement si on fait ceci :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
     new ObjectOutputStream(new FileOutputStream("file"));
    Une exception dans le constructeur ObjectOutputStream nous empêcherait de fermer le fichier pourtant bien ouvert, puisqu'on aurait plus de référence vers ce dernier

    La meilleure solution serait donc d'utiliser deux try/finally :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    	public void writeFile(Object t, String fichierSortie) throws IOException {
    		OutputStream fos = new BufferedOutputStream(new FileOutputStream(fichierSortie + ".serial"));
    		try {
    			ObjectOutputStream out = new ObjectOutputStream(fos);
    			try {
    				out.writeObject(t);
    			} finally {
    				out.close();
    			}
    		} finally {
    			fos.close();
    		}
    	}

    A noter que Java 7 devrait intégrer une syntaxe plus clair pour gérer ces cas là...


    a++

    PS : J'ai viré la syntaxe generics qui ne sert à rien ici. Au pire tu pourrais utiliser le type Serializable à la place de Object...

  8. #8
    Inactif   Avatar de Deallyra
    Profil pro
    Étudiant
    Inscrit en
    Février 2007
    Messages
    1 997
    Détails du profil
    Informations personnelles :
    Âge : 37
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Février 2007
    Messages : 1 997
    Par défaut
    Donc, pour la désérialisation, tu préconises un code allant en ce sens :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
     
        public void deserializer(Object t, String fichierEntree){
            InputStream fis = new BufferedInputStream(new FileInputStream(fichierEntree + ".serial"));
            try {
                ObjectInputStream in= new ObjectInputStream(fis);
                try {
                    t = in.readObject();
                    System.out.println(t + " a ete deserialise");
                } finally {
                        in.close();
                }
            } finally {
                fis.close();
            }
        }
    PS : J'ai viré la syntaxe generics qui ne sert à rien ici. Au pire tu pourrais utiliser le type Serializable à la place de Object...
    Object acceptera n'importe quel objet même non implémentant sérializable c'est ça ?
    *Si la réponse vous convient, n'oubliez pas le tag
    *Exprimez vous dans un français correct; on prend le temps de vous lire, prenez le temps de bien écrire.
    *Et comment on interprète votre code? N'oubliez pas la balise!

    *Pour une mise en page simple avec des divs.
    *Pour faire des formulaires xHTML CSS.

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

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

    Informations forums :
    Inscription : Avril 2007
    Messages : 25 482
    Par défaut
    sauf que ton code, après avoir désérialiser, il fait rien du tout de la valeur là. Il l'attribue à t qui est une variable locale. Ca disparaitra dans les méandre du garbage collector dès la sortie de la méthode

  10. #10
    Inactif   Avatar de Deallyra
    Profil pro
    Étudiant
    Inscrit en
    Février 2007
    Messages
    1 997
    Détails du profil
    Informations personnelles :
    Âge : 37
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Février 2007
    Messages : 1 997
    Par défaut
    Hum... T est un objet que je lui envoies par référence, en paramètre...

    Donc il devrait être modifié non? O.o
    *Si la réponse vous convient, n'oubliez pas le tag
    *Exprimez vous dans un français correct; on prend le temps de vous lire, prenez le temps de bien écrire.
    *Et comment on interprète votre code? N'oubliez pas la balise!

    *Pour une mise en page simple avec des divs.
    *Pour faire des formulaires xHTML CSS.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. programmer en object orienté en JS la différence entre deux méthodes ?
    Par nicko_73 dans le forum Général JavaScript
    Réponses: 5
    Dernier message: 03/11/2009, 13h24
  2. Différence entre deux méthodes
    Par newmar dans le forum Débuter avec Java
    Réponses: 9
    Dernier message: 02/04/2008, 19h29
  3. Différence entre deux dates
    Par pittzz dans le forum Oracle
    Réponses: 5
    Dernier message: 18/07/2005, 12h24
  4. Comment obtenir la différence entre deux dates ?
    Par jbat dans le forum Langage
    Réponses: 4
    Dernier message: 02/06/2005, 09h34
  5. Résultats erroné différence entre deux types TDateTime
    Par Alghero dans le forum C++Builder
    Réponses: 6
    Dernier message: 12/03/2004, 17h03

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