Domanda

Cosa si intende per "serializzazione degli oggetti"?Potete spiegarlo con qualche esempio?

È stato utile?

Soluzione

La serializzazione è la conversione di un oggetto in una serie di byte, in modo che l'oggetto possa essere facilmente salvato nella memoria permanente o trasmesso in streaming attraverso un collegamento di comunicazione. Il flusso di byte può quindi essere deserializzato, convertito in una replica dell'oggetto originale.

Altri suggerimenti

Puoi considerare la serializzazione come il processo di conversione di un'istanza di oggetto in una sequenza di byte (che può essere binaria o non dipendente dall'implementazione).

È molto utile quando si desidera trasmettere dati di un oggetto attraverso la rete, ad esempio da una JVM a un'altra.

In Java, il meccanismo di serializzazione è integrato nella piattaforma, ma è necessario implementare l'interfaccia Serializable per rendere serializzabile un oggetto.

Puoi anche impedire la serializzazione di alcuni dati nel tuo oggetto contrassegnando l'attributo come transitorio .

Finalmente puoi sovrascrivere il meccanismo predefinito e fornire il tuo; questo può essere adatto in alcuni casi speciali. Per fare ciò, usi una delle funzioni nascoste in java .

È importante notare che ciò che viene serializzato è il " valore " dell'oggetto o dei contenuti e non la definizione della classe. Pertanto i metodi non sono serializzati.

Ecco un esempio molto semplice con commenti per facilitarne la lettura:

import java.io.*;
import java.util.*;

// This class implements "Serializable" to let the system know
// it's ok to do it. You as programmer are aware of that.
public class SerializationSample implements Serializable {

    // These attributes conform the "value" of the object.

    // These two will be serialized;
    private String aString = "The value of that string";
    private int    someInteger = 0;

    // But this won't since it is marked as transient.
    private transient List<File> unInterestingLongLongList;

    // Main method to test.
    public static void main( String [] args ) throws IOException  { 

        // Create a sample object, that contains the default values.
        SerializationSample instance = new SerializationSample();

        // The "ObjectOutputStream" class has the default 
        // definition to serialize an object.
        ObjectOutputStream oos = new ObjectOutputStream( 
                               // By using "FileOutputStream" we will 
                               // Write it to a File in the file system
                               // It could have been a Socket to another 
                               // machine, a database, an in memory array, etc.
                               new FileOutputStream(new File("o.ser")));

        // do the magic  
        oos.writeObject( instance );
        // close the writing.
        oos.close();
    }
}

Quando eseguiamo questo programma, il file " o.ser " viene creato e possiamo vedere cosa è successo dietro.

Se cambiamo il valore di: someInteger , ad esempio Integer.MAX_VALUE , potremmo confrontare l'output per vedere qual è la differenza.

Ecco uno screenshot che mostra esattamente quella differenza:

alt text

Riesci a individuare le differenze? ;)

Esiste un ulteriore campo rilevante nella serializzazione Java: serialversionUID ma immagino che questo è già troppo lungo per coprirlo.

Osare rispondere alla domanda di 6 anni, aggiungendo una comprensione di altissimo livello per le persone che non conoscono Java

  

Che cos'è la serializzazione?

Conversione di un oggetto in byte e byte nuovamente in oggetto (Deserializzazione).

  

quando viene utilizzata la serializzazione?

Quando vogliamo persistere nell'oggetto. Quando vogliamo che l'oggetto esista oltre la durata della JVM.

  

Esempio nel mondo reale:

Bancomat: quando il titolare del conto tenta di prelevare denaro dal server tramite bancomat, le informazioni sul titolare del conto come i dettagli del prelievo vengono serializzate e inviate al server in cui i dettagli sono deserializzati e utilizzati per eseguire operazioni.

  

Come viene eseguita la serializzazione in java.

  1. Implementa java.io.Serializable interfaccia (interfaccia marker quindi nessun metodo da implementare).

  2. Persistere l'oggetto: utilizzare la classe java.io.ObjectOutputStream, un flusso di filtro che è un wrapper attorno a un flusso di byte di livello inferiore (per scrivere l'oggetto su file system o trasferire un oggetto appiattito su un filo di rete e ricostruito sul dall'altra parte).

    • writeObject(<<instance>>) - per scrivere un oggetto
    • readObject() - per leggere un oggetto serializzato
  

Ricorda:

Quando si serializza un oggetto, verrà salvato solo lo stato dell'oggetto, non il file o i metodi della classe dell'oggetto.

Quando si serializza un oggetto a 2 byte, viene visualizzato un file serializzato di 51 byte.

  

Passa come l'oggetto viene serializzato e deserializzato.

Risposta per: come è stato convertito in file di 51 byte?

  • Prima scrive i dati magici del flusso di serializzazione (STREAM_MAGIC = " AC ED " e STREAM_VERSION = versione della JVM).
  • Quindi scrive i metadati della classe associata a un'istanza (lunghezza della classe, nome della classe, serialVersionUID).
  • Quindi scrive in modo ricorsivo i metadati della superclasse fino a quando non trova java.lang.Object.
  • Quindi inizia con i dati effettivi associati all'istanza.
  • Infine, scrive i dati degli oggetti associati all'istanza a partire dai metadati sul contenuto effettivo.
  

Se sei interessato a maggiori informazioni di approfondimento sulla serializzazione Java, consulta questo link .

Modifica : un altro ottimo link leggere.

Questo risponderà ad alcune domande frequenti:

  1. Come non serializzare nessun campo in classe.
    Risposta: usa la parola chiave temporanea

  2. Quando la classe figlio è serializzata, la classe genitore viene serializzata?
    Risp: No, se il genitore non sta estendendo il campo genitori dell'interfaccia serializzabile non viene serializzato.

  3. Quando parent è serializzato, la classe child viene serializzata?
    Risp: Sì, per impostazione predefinita anche le classi secondarie vengono serializzate.

  4. Come evitare che le classi secondarie vengano serializzate?
    Ans: a. Sovrascrivi il metodo writeObject e readObject e lancia NotSerializableException.

    b. inoltre puoi contrassegnare tutti i campi transitori nella classe figlio.

  5. Alcune classi a livello di sistema come Thread, OutputStream e le sue sottoclassi e Socket non sono serializzabili.

La serializzazione richiede un " live " oggetto in memoria e convertendolo in un formato che può essere archiviato da qualche parte (es. in memoria, su disco) e successivamente " deserializzato " di nuovo in un oggetto vivo.

Mi è piaciuto il modo in cui @OscarRyz si presenta. Anche se qui continuo la storia della serializzazione che è stata originariamente scritta da @amitgupta.

Anche se conoscendo la struttura delle classi dei robot e avendo dati serializzati, gli scienziati della Terra non sono stati in grado di deserializzare i dati che possono far funzionare i robot.

Exception in thread "main" java.io.InvalidClassException:
SerializeMe; local class incompatible: stream classdesc
:

Gli scienziati di Mars stavano aspettando il pagamento completo. Una volta effettuato il pagamento, gli scienziati di Mars hanno condiviso il serialversionUID con gli scienziati della Terra. Lo scienziato della Terra lo ha impostato sulla classe dei robot e tutto è andato bene.

I miei due centesimi dal mio blog:

Ecco una spiegazione dettagliata della serializzazione:(il mio blog)

Serializzazione:

La serializzazione è il processo di persistenza dello stato di un oggetto.Viene rappresentato e memorizzato sotto forma di una sequenza di byte.Questo può essere memorizzato in un file.Il processo per leggere lo stato dell'oggetto dal file e ripristinarlo è chiamato deserializzazione.

Qual è la necessità della serializzazione?

Nell'architettura moderna, è sempre necessario memorizzare lo stato dell'oggetto e quindi recuperarlo.Ad esempio in Hibernate, per memorizzare un oggetto dovremmo rendere la classe Serializable.Ciò che fa è che una volta che lo stato dell'oggetto viene salvato sotto forma di byte, può essere trasferito a un altro sistema che può quindi leggere dallo stato e recuperare la classe.Lo stato dell'oggetto può provenire da un database o da una jvm diversa o da un componente separato.Con l'aiuto della serializzazione possiamo recuperare lo stato dell'oggetto.

Codice Esempio e spiegazione:

Per prima cosa diamo un'occhiata alla classe dell'oggetto:

public class Item implements Serializable{

    /**
    *  This is the Serializable class
    */
    private static final long serialVersionUID = 475918891428093041L;
    private Long itemId;
    private String itemName;
    private transient Double itemCostPrice;
    public Item(Long itemId, String itemName, Double itemCostPrice) {
        super();
        this.itemId = itemId;
        this.itemName = itemName;
        this.itemCostPrice = itemCostPrice;
      }

      public Long getItemId() {
          return itemId;
      }

     @Override
      public String toString() {
          return "Item [itemId=" + itemId + ", itemName=" + itemName + ", itemCostPrice=" + itemCostPrice + "]";
       }


       public void setItemId(Long itemId) {
           this.itemId = itemId;
       }

       public String getItemName() {
           return itemName;
       }
       public void setItemName(String itemName) {
            this.itemName = itemName;
        }

       public Double getItemCostPrice() {
            return itemCostPrice;
        }

        public void setItemCostPrice(Double itemCostPrice) {
             this.itemCostPrice = itemCostPrice;
        }
}

Nel codice sopra si può vedere che Articolo implementa la classe Serializzabile.

Questa è l'interfaccia che consente a una classe di essere serializzabile.

Ora possiamo vedere una variabile chiamata serialVersionUID è inizializzato sulla variabile Long.Questo numero viene calcolato dal compilatore in base allo stato della classe e agli attributi della classe.Questo è il numero che aiuterà la jvm a identificare lo stato di un oggetto quando legge lo stato dell'oggetto dal file.

Per questo possiamo dare un'occhiata alla documentazione ufficiale Oracle:

La runtime di serializzazione si associa a ciascuna numero di versione di classe serializzabile, chiamato serialversionuid, che viene utilizzato durante la deserializzazione per verificare che il mittente e il ricevitore di un oggetto serializzato abbiano caricato classi per quell'oggetto che sono compatibili con rispetto per la serializzazione.Se il ricevitore ha caricato una classe per l'oggetto che ha un serialversionuid diverso da quello della classe del mittente corrispondente, allora la deserializzazione si tradurrà in una ClassException invalidassexception.Una classe serializzabile può dichiarare esplicitamente la propria serialversionuid dichiarando un campo chiamato "serialversionuid" che deve essere statico, finale e di tipo lungo:ANY-ACCESS-MODIFIER statico finale lungo serialVersionUID = 42L;Se un la classe serializable non dichiara esplicitamente un serialVersionUID, poi il runtime di serializzazione calcolerà un default serialVersionUID valore per quella classe basato su vari aspetti della classe, come descritto nella Java(TM) Object Serialization Specifiche.Tuttavia, si raccomanda vivamente che tutte le classi serializzabili dichiarano esplicitamente i valori serialVersionUID, poiché il calcolo predefinito serialVersionUID è altamente sensibile alla classe dettagli che possono variare a seconda delle implementazioni del compilatore, e possono quindi provocare InvalidClassExceptions inaspettati durante deserializzazione.Pertanto, per garantire un serialVersionUID coerente valore tra diverse implementazioni del compilatore java, un serializzabile class deve dichiarare un valore serialVersionUID esplicito.Si tratta anche di si consiglia vivamente che le dichiarazioni esplicite serialVersionUID utilizzino il modificatore privato ove possibile, dal momento che tali dichiarazioni si applicano solo a i campi class--serialVersionUID che dichiarano immediatamente non sono utili come membri ereditari.

Se hai notato che abbiamo utilizzato un'altra parola chiave, ovvero transitorio.

Se un campo non è serializzabile, deve essere contrassegnato come transitorio.Qui abbiamo segnato il itemCostoPrezzo come transitorio e non voglio che venga scritto in un file

Ora diamo un'occhiata a come scrivere lo stato di un oggetto nel file e poi leggerlo da lì.

public class SerializationExample {

    public static void main(String[] args){
        serialize();
       deserialize();
    } 

    public static void serialize(){

         Item item = new Item(1L,"Pen", 12.55);
         System.out.println("Before Serialization" + item);

         FileOutputStream fileOut;
         try {
             fileOut = new FileOutputStream("/tmp/item.ser");
             ObjectOutputStream out = new ObjectOutputStream(fileOut);
             out.writeObject(item);
             out.close();
             fileOut.close();
             System.out.println("Serialized data is saved in /tmp/item.ser");
           } catch (FileNotFoundException e) {

                  e.printStackTrace();
           } catch (IOException e) {

                  e.printStackTrace();
           }
      }

    public static void deserialize(){
        Item item;

        try {
                FileInputStream fileIn = new FileInputStream("/tmp/item.ser");
                ObjectInputStream in = new ObjectInputStream(fileIn);
                item = (Item) in.readObject();
                System.out.println("Serialized data is read from /tmp/item.ser");
                System.out.println("After Deserialization" + item);
        } catch (FileNotFoundException e) {
                e.printStackTrace();
        } catch (IOException e) {
               e.printStackTrace();
        } catch (ClassNotFoundException e) {
               e.printStackTrace();
        }
     }
}

In alto possiamo vedere un esempio di serializzazione e deserializzazione di un oggetto.

Per questo abbiamo utilizzato due classi.Per serializzare l'oggetto abbiamo utilizzato ObjectOutputStream.Abbiamo utilizzato il metodo writeObject per scrivere l'oggetto nel file.

Per la deserializzazione abbiamo utilizzato ObjectInputStream che legge l'oggetto dal file.Utilizza readObject per leggere i dati dell'oggetto dal file.

L'output del codice sopra sarebbe come:

Before SerializationItem [itemId=1, itemName=Pen, itemCostPrice=12.55]
Serialized data is saved in /tmp/item.ser
After DeserializationItem [itemId=1, itemName=Pen, itemCostPrice=null]

Notare che itemCostoPrezzo dall'oggetto deserializzato è nullo poiché non era scritto.

Abbiamo già discusso le basi della serializzazione Java nella parte I di questo articolo.

Ora parliamone approfonditamente e di come funziona.

Per prima cosa iniziamo con il serialversionuid.

IL serialVersionUID viene utilizzato come controllo di versione in una classe Serializable.

Se non dichiari esplicitamente un serialVersionUID, JVM lo farà automaticamente per te, in base a varie proprietà della classe Serializable.

Algoritmo di calcolo di serialversionuid di Java (Leggi maggiori dettagli qui)

  1. Il nome della classe.
    1. I modificatori di classe scritti come numero intero a 32 bit.
    2. Il nome di ciascuna interfaccia ordinata per nome.
    3. Per ogni campo della classe ordinato per nome del campo (eccetto i campi privati ​​statici e temporanei privati:Il nome del campo.I modificatori del campo scritti come un numero intero a 32 bit.Il descrittore del campo.
    4. Se esiste un inizializzatore di classe, scrivi quanto segue:Il nome del metodo, .
    5. Il modificatore del metodo, java.lang.reflect.Modifier.STATIC, scritto come numero intero a 32 bit.
    6. Il descrittore del metodo, ()V.
    7. Per ogni costruttore non privato ordinato per nome del metodo e firma:Il nome del metodo, .I modificatori del metodo scritto come un numero intero a 32 bit.Il descrittore del metodo.
    8. Per ciascun metodo non privato ordinato per nome del metodo e firma:Il nome del metodo.I modificatori del metodo scritto come un numero intero a 32 bit.Il descrittore del metodo.
    9. L'algoritmo SHA-1 viene eseguito sul flusso di byte prodotto da DataOutputStream e produce cinque valori a 32 bit sha[0..4].Il valore di hash è assemblato dal primo e dal secondo valori a 32 bit del Digest del messaggio SHA-1.Se il risultato del Digest del messaggio, le cinque parole a 32 bit H0 H1 H2 H3 H4, sono in un array di cinque valori INT denominati SHA, il valore di hash verrebbe calcolato come segue:
    long hash = ((sha[0] >>> 24) & 0xFF) |
>            ((sha[0] >>> 16) & 0xFF) << 8 |
>            ((sha[0] >>> 8) & 0xFF) << 16 |
>            ((sha[0] >>> 0) & 0xFF) << 24 |
>            ((sha[1] >>> 24) & 0xFF) << 32 |
>            ((sha[1] >>> 16) & 0xFF) << 40 |
>            ((sha[1] >>> 8) & 0xFF) << 48 |
>        ((sha[1] >>> 0) & 0xFF) << 56;

Algoritmo di serializzazione di Java

L'algoritmo per serializzare un oggetto è descritto come di seguito:
1.Scrive i metadati della classe associata a un'istanza.
2.Scrive ricorsivamente la descrizione della superclasse finché non la trova java.lang.oggetto.
3.Una volta terminata la scrittura delle informazioni sui metadati, inizia con i dati effettivi associati all'istanza.Ma questa volta, inizia dalla superclasse più alta.
4.Scrive ricorsivamente i dati associati all'istanza, a partire dalla meno superclasse fino alla classe più derivata.

Cose da tenere a mente:

  1. I campi statici in una classe non possono essere serializzati.

    public class A implements Serializable{
         String s;
         static String staticString = "I won't be serializable";
    }
    
  2. Se il serialversionuid è diverso nella classe di lettura, genererà un file InvalidClassException eccezione.

  3. Se una classe implementa serializzabile, anche tutte le sue sottoclassi saranno serializzabili.

    public class A implements Serializable {....};
    
    public class B extends A{...} //also Serializable
    
  4. Se una classe ha un riferimento ad un'altra classe, tutti i riferimenti devono essere serializzabili altrimenti il ​​processo di serializzazione non verrà eseguito.In tal caso, NotSerializableException viene lanciato in fase di esecuzione.

Per esempio:

public class B{
     String s,
     A a; // class A needs to be serializable i.e. it must implement Serializable
}

La serializzazione significa oggetti persistenti in Java. Se si desidera salvare lo stato dell'oggetto e ricostruire lo stato in un secondo momento (potrebbe essere in un'altra JVM), è possibile utilizzare la serializzazione.

Nota che le proprietà di un oggetto verranno salvate. Se vuoi resuscitare di nuovo l'oggetto, dovresti avere il file di classe, perché verranno memorizzate solo le variabili membro e non le funzioni membro.

ad esempio:

ObjectInputStream oos = new ObjectInputStream(                                 
                                 new FileInputStream(  new File("o.ser")) ) ;
SerializationSample SS = (SearializationSample) oos.readObject();

Searializable è un'interfaccia marker che indica che la tua classe è serializzabile. L'interfaccia Marker significa che è solo un'interfaccia vuota e l'utilizzo di tale interfaccia avviserà la JVM che questa classe può essere resa serializzabile.

La serializzazione è il processo di conversione dello stato di un oggetto in bit in modo che possa essere memorizzato su un disco rigido. Quando si deserializza lo stesso oggetto, manterrà il suo stato in seguito. Ti consente di ricreare oggetti senza dover salvare manualmente le proprietà degli oggetti.

http://en.wikipedia.org/wiki/Serialization

La serializzazione è il processo di salvataggio di un oggetto in un supporto di memorizzazione (come un file o un buffer di memoria) o di trasmetterlo su una connessione di rete in forma binaria. Gli oggetti serializzati sono indipendenti dalla JVM e possono essere nuovamente serializzati da qualsiasi JVM. In questo caso il & Quot; in memory & Quot; lo stato degli oggetti java viene convertito in un flusso di byte. Questo tipo di file non può essere compreso dall'utente. È un tipo speciale di oggetto, cioè riutilizzato dalla JVM (Java Virtual Machine). Questo processo di serializzazione di un oggetto è anche chiamato sgonfiamento o marshalling di un oggetto.

L'oggetto da serializzare deve implementare java.io.Serializable Interfaccia. Il meccanismo di serializzazione predefinito per un oggetto scrive la classe dell'oggetto, la firma della classe e i valori di tutti i campi non transitori e non statici.

class ObjectOutputStream extends java.io.OutputStream implements ObjectOutput,
L'interfaccia

ObjectOutput estende l'interfaccia DataOutput e aggiunge metodi per serializzare oggetti e scrivere byte nel file. ObjectOutputStream estende java.io.OutputStream e implementa l'interfaccia ObjectOutputStream( ). Serializza oggetti, matrici e altri valori su un flusso. Quindi il costruttore di FileOuputStream è scritto come:

ObjectOutput ObjOut = new ObjectOutputStream(new FileOutputStream(f));

Il codice sopra è stato utilizzato per creare l'istanza della classe ObjectInputStream con il costruttore java.io.InputStream che utilizza l'istanza di ObjectInput come parametro.

L'interfaccia FileInputStream viene utilizzata implementando la classe ObjectInputStream(). <=> è costruito per serializzare l'oggetto.

Deserializzazione di un oggetto in java

L'operazione opposta della serializzazione si chiama deserializzazione, ovvero estrarre i dati da una serie di byte è nota come deserializzazione, che è anche chiamata inflazione o smascheramento.

<=> estende <=> e implementa l'interfaccia <=>. Deserializza oggetti, matrici e altri valori da un flusso di input. Quindi il costruttore di <=> è scritto come:

ObjectInputStream obj = new ObjectInputStream(new FileInputStream(f));

Il codice di cui sopra del programma crea l'istanza della classe <=> per deserializzare quel file che era stato serializzato dalla classe <=>. Il codice sopra crea l'istanza usando l'istanza della classe <=> che contiene l'oggetto file specificato che deve essere deserializzato perché il costruttore <=> necessita del flusso di input.

Java Serializzazione oggetti

 inserisci qui la descrizione dell'immagine

Serialization è un meccanismo per trasformare un grafico di oggetti Java in una matrice di byte per l'archiviazione (to disk file) o la trasmissione (across a network), quindi utilizzando deserializzazione possiamo ripristinare il grafico degli oggetti. I grafici degli oggetti vengono ripristinati correttamente utilizzando un meccanismo di condivisione di riferimento. Ma prima di archiviare, controlla se serialVersionUID da input-file / network e .class file serialVersionUID sono uguali. In caso contrario, lancia un java.io.InvalidClassException.

  

Ogni classe con versione deve identificare la versione della classe originale per la quale è in grado di scrivere flussi e dalla quale può leggere. Ad esempio, una classe con versione deve dichiarare:

     

Sintassi serialVersionUID

// ANY-ACCESS-MODIFIER static final long serialVersionUID = (64-bit has)L;
private static final long serialVersionUID = 3487495895819393L;

serialVersionUID è essenziale per il processo di serializzazione. Ma è facoltativo per lo sviluppatore aggiungerlo nel file sorgente Java. Se un serialVersionUID non è incluso, il runtime di serializzazione genererà un serialVersionUID e lo assocerà alla classe. L'oggetto serializzato conterrà questo serialVersionUID insieme ad altri dati.

Nota - Si consiglia vivamente a tutte le classi serializzabili di dichiarare esplicitamente un serialVersionUID, since the default serialVersionUID computation is highly sensitive to class details that may vary depending on compiler implementations , e può quindi provocare conflitti imprevisti di serialVersionUID durante la deserializzazione, causando la deserializzazione a fallire.

Ispezione delle classi serializzabili

 inserisci qui la descrizione dell'immagine


  

Un oggetto Java è solo serializzabile. se una classe o una delle sue superclasse implementa l'interfaccia java.io.Serializable    o la sua interfaccia secondaria, java.io.Externalizable .

  • Una classe deve implementare interfaccia java.io.Serializable per serializzare correttamente il suo oggetto. Serializable è un'interfaccia marker e utilizzata per informare il compilatore che alla classe che lo implementa deve essere aggiunto un comportamento serializzabile. Qui Java Virtual Machine (JVM) è responsabile della sua serializzazione automatica.

      

    Parola chiave temporanea: java.io.Serializable interface

         

    Durante la serializzazione di un oggetto, se non vogliamo che determinati membri dei dati dell'oggetto vengano serializzati, possiamo usare il modificatore transitorio. La parola chiave temporanea impedirà la serializzazione di quel membro di dati.

         
        
    • I campi dichiarati come transitori o statici vengono ignorati dal processo di serializzazione.
    •   
         
        

    TRANSIENT & Amp; VOLATILE

      
    +--------------+--------+-------------------------------------+
    |  Flag Name   |  Value | Interpretation                      |
    +--------------+--------+-------------------------------------+
    | ACC_VOLATILE | 0x0040 | Declared volatile; cannot be cached.|
    +--------------+--------+-------------------------------------+
    |ACC_TRANSIENT | 0x0080 | Declared transient; not written or  |
    |              |        | read by a persistent object manager.|
    +--------------+--------+-------------------------------------+
    
    class Employee implements Serializable {
        private static final long serialVersionUID = 2L;
        static int id;
    
        int eno; 
        String name;
        transient String password; // Using transient keyword means its not going to be Serialized.
    }
    
  • L'implementazione dell'interfaccia Externalizable consente all'oggetto di assumere il controllo completo sul contenuto e sul formato del modulo serializzato dell'oggetto. I metodi dell'interfaccia Externalizable, writeExternal e readExternal, vengono chiamati per salvare e ripristinare lo stato degli oggetti. Se implementati da una classe, possono scrivere e leggere il proprio stato usandotutti i metodi di ObjectOutput e ObjectInput. È responsabilità degli oggetti gestire qualsiasi versione che si verifica.

    class Emp implements Externalizable {
        int eno; 
        String name;
        transient String password; // No use of transient, we need to take care of write and read.
    
        @Override
        public void writeExternal(ObjectOutput out) throws IOException {
            out.writeInt(eno);
            out.writeUTF(name);
            //out.writeUTF(password);
        }
        @Override
        public void readExternal(ObjectInput in) throws IOException, ClassNotFoundException {
            this.eno = in.readInt();
            this.name = in.readUTF();
            //this.password = in.readUTF(); // java.io.EOFException
        }
    }
    
  • Solo gli oggetti che supportano l'interfaccia java.io.Serializable o java.io.Externalizable possono essere flussi written to / read from. La classe di ogni oggetto serializzabile viene codificata includendo il nome e la firma della classe, i valori dei campi e delle matrici dell'oggetto e la chiusura di qualsiasi altro oggetto a cui fanno riferimento gli oggetti iniziali.

Esempio serializzabile per file

public class SerializationDemo {
    static String fileName = "D:/serializable_file.ser";

    public static void main(String[] args) throws IOException, ClassNotFoundException, InstantiationException, IllegalAccessException {
        Employee emp = new Employee( );
        Employee.id = 1; // Can not Serialize Class data.
        emp.eno = 77;
        emp.name = "Yash";
        emp.password = "confidential";
        objects_WriteRead(emp, fileName);

        Emp e = new Emp( );
        e.eno = 77;
        e.name = "Yash";
        e.password = "confidential";
        objects_WriteRead_External(e, fileName);

        /*String stubHost = "127.0.0.1";
        Integer anyFreePort = 7777;
        socketRead(anyFreePort); //Thread1
        socketWrite(emp, stubHost, anyFreePort); //Thread2*/

    }
    public static void objects_WriteRead( Employee obj, String serFilename ) throws IOException{
        FileOutputStream fos = new FileOutputStream( new File( serFilename ) );
        ObjectOutputStream objectOut = new ObjectOutputStream( fos );
        objectOut.writeObject( obj );
        objectOut.close();
        fos.close();

        System.out.println("Data Stored in to a file");

        try {
            FileInputStream fis = new FileInputStream( new File( serFilename ) );
            ObjectInputStream ois = new ObjectInputStream( fis );
            Object readObject;
            readObject = ois.readObject();
            String calssName = readObject.getClass().getName();
            System.out.println("Restoring Class Name : "+ calssName); // InvalidClassException

            Employee emp = (Employee) readObject;
            System.out.format("Obj[No:%s, Name:%s, Pass:%s]", emp.eno, emp.name, emp.password);

            ois.close();
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        }
    }
    public static void objects_WriteRead_External( Emp obj, String serFilename ) throws IOException {
        FileOutputStream fos = new FileOutputStream(new File( serFilename ));
        ObjectOutputStream objectOut = new ObjectOutputStream( fos );

        obj.writeExternal( objectOut );
        objectOut.flush();

        fos.close();

        System.out.println("Data Stored in to a file");

        try {
            // create a new instance and read the assign the contents from stream.
            Emp emp = new Emp();

            FileInputStream fis = new FileInputStream(new File( serFilename ));
            ObjectInputStream ois = new ObjectInputStream( fis );

            emp.readExternal(ois);

            System.out.format("Obj[No:%s, Name:%s, Pass:%s]", emp.eno, emp.name, emp.password);

            ois.close();
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        }
    }
}

Esempio serializzabile su rete

Distribuire lo stato dell'oggetto su spazi di indirizzi diversi, sia in processi diversi sullo stesso computer, o anche in più computer collegati tramite una rete, ma che collaborano condividendo dati e invocando metodi.

/**
 * Creates a stream socket and connects it to the specified port number on the named host. 
 */
public static void socketWrite(Employee objectToSend, String stubHost, Integer anyFreePort) {
    try { // CLIENT - Stub[marshalling]
        Socket client = new Socket(stubHost, anyFreePort);
        ObjectOutputStream out = new ObjectOutputStream(client.getOutputStream());
        out.writeObject(objectToSend);
        out.flush();
        client.close();
    } catch (IOException e) {
        e.printStackTrace();
    }
}
// Creates a server socket, bound to the specified port. 
public static void socketRead(  Integer anyFreePort ) {
    try { // SERVER - Stub[unmarshalling ]
        ServerSocket serverSocket = new ServerSocket( anyFreePort );
        System.out.println("Server serves on port and waiting for a client to communicate");
            /*System.in.read();
            System.in.read();*/

        Socket socket = serverSocket.accept();
        System.out.println("Client request to communicate on port server accepts it.");

        ObjectInputStream in = new ObjectInputStream(socket.getInputStream());
        Employee objectReceived = (Employee) in.readObject();
        System.out.println("Server Obj : "+ objectReceived.name );

        socket.close();
        serverSocket.close();
    } catch (IOException | ClassNotFoundException e) {
        e.printStackTrace();
    }
}

@see

La serializzazione è il processo di trasformazione di un oggetto Java in array di byte e quindi di nuovo in oggetto con lo stato conservato. Utile per varie cose come l'invio di oggetti in rete o la memorizzazione nella cache di oggetti sul disco.

Leggi di più da questo breve articolo che spiega abbastanza bene la programmazione della parte del processo , quindi passare a Serializable javadoc . Potresti anche essere interessato a leggere questa domanda correlata .

Restituisce il file come oggetto: http://www.tutorialspoint.com/java/ java_serialization.htm

        import java.io.*;

        public class SerializeDemo
        {
           public static void main(String [] args)
           {
              Employee e = new Employee();
              e.name = "Reyan Ali";
              e.address = "Phokka Kuan, Ambehta Peer";
              e.SSN = 11122333;
              e.number = 101;

              try
              {
                 FileOutputStream fileOut =
                 new FileOutputStream("/tmp/employee.ser");
                 ObjectOutputStream out = new ObjectOutputStream(fileOut);
                 out.writeObject(e);
                 out.close();
                 fileOut.close();
                 System.out.printf("Serialized data is saved in /tmp/employee.ser");
              }catch(IOException i)
              {
                  i.printStackTrace();
              }
           }
        }

    import java.io.*;
    public class DeserializeDemo
    {
       public static void main(String [] args)
       {
          Employee e = null;
          try
          {
             FileInputStream fileIn = new FileInputStream("/tmp/employee.ser");
             ObjectInputStream in = new ObjectInputStream(fileIn);
             e = (Employee) in.readObject();
             in.close();
             fileIn.close();
          }catch(IOException i)
          {
             i.printStackTrace();
             return;
          }catch(ClassNotFoundException c)
          {
             System.out.println("Employee class not found");
             c.printStackTrace();
             return;
          }
          System.out.println("Deserialized Employee...");
          System.out.println("Name: " + e.name);
          System.out.println("Address: " + e.address);
          System.out.println("SSN: " + e.SSN);
          System.out.println("Number: " + e.number);
        }
    }

|*| Serializzazione di una classe :Conversione di un oggetto in byte e di nuovo byte in oggetto (Deserializzazione).

class NamCls implements Serializable
{
    int NumVar;
    String NamVar;
}

|=> La serializzazione degli oggetti è il processo di conversione dello stato di un oggetto in vapore di byte.

  • |-> Implementare quando si desidera che l'oggetto esista oltre la durata della JVM.
  • |-> L'oggetto serializzato può essere archiviato nel database.
  • |-> Gli oggetti serializzabili non possono essere letti e compresi dagli esseri umani, quindi possiamo ottenere sicurezza.

|=> La deserializzazione degli oggetti è il processo per ottenere lo stato di un oggetto e memorizzarlo in un oggetto (java.lang.Object).

  • |-> Prima di memorizzare il suo stato controlla se serialVersionUID dal file di input/rete e dal file .class serialVersionUID sono uguali.
    &nbsp&nbspIn caso contrario, viene lanciata java.io.InvalidClassException.

|=> Un oggetto Java è serializzabile solo se è la sua classe o una qualsiasi delle sue superclassi

  • implementa l'interfaccia java.io.Serializable o
  • la sua sottointerfaccia, java.io.Externalizable.

|=> I campi statici in una classe non possono essere serializzati.

class NamCls implements Serializable
{
    int NumVar;
    static String NamVar = "I won't be serializable";;
}

|=> Se non vuoi serializzare una variabile di una classe usa la parola chiave transitoria

class NamCls implements Serializable
{
    int NumVar;
    transient String NamVar;
}

|=> Se una classe implementa serializzabile, anche tutte le sue sottoclassi saranno serializzabili.

|=> Se una classe ha un riferimento ad un'altra classe, tutti i riferimenti devono essere serializzabili altrimenti il ​​processo di serializzazione non verrà eseguito.In tal caso,
NotSerializableException viene generata in fase di esecuzione.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top