Pagina 1 di 2 1 2 ultimoultimo
Visualizzazione dei risultati da 1 a 10 su 11
  1. #1

    [Java] ObjectOutputStream writeObject NotSerializableException

    Ciao a tutti,

    sono un principiante della programmazione java e mi sono imbattuto in un problema che vi espongo. Devo salvare su file un hashmap che ha per chiave una String e per valore una classe personalizzata. Ho trovato numerosi post su quest'argomento ma non riesco a capire dove stia il mio errore. La classe da me creata implementa l'interfaccia Serializable e contiene solo tipi String e int (ho provato anche con Integer ma senza successo).

    Ho provato ad aggiungere i metodi readObject e writeObject (vuoti) con il risultato che non ottengo più l'errore ma non viene salvato il valore, viene cioè salvato ("Test_1", null) (non mi sembra sia la soluzione corretta e quindi l'ho rimossa).

    Qualcuno sarebbe così gentile da dirmi dove sto sbagliando?

    Di seguito il codice:

    codice:
    import java.io.FileOutputStream;
    import java.io.ObjectOutputStream;
    import java.io.Serializable;
    import java.util.HashMap;
    
    public class SalvaOggetti {
    
    	class Persona implements Serializable {
    		String nome;
    		String cognome;
    		String indirizzo;
    		int età;
    		
    		public Persona() {
    			
    		}
    		public Persona(String nome, String cognome, String indirizzo, int età) {
    			this.nome = nome;
    			this.cognome = cognome;
    			this.indirizzo = indirizzo;
    			this.età = età;
    		}
    	}
    	
    	HashMap<String, Persona> hashmap_persona = new HashMap<String, Persona>();
    	ObjectOutputStream oos;
    	
    	public SalvaOggetti() {
    		hashmap_persona.put("Test_1", new Persona("Mario", "Rossi", "Casa sua", 30));
    		
    		try {
    			oos = new ObjectOutputStream(new FileOutputStream("prova.txt"));
    			oos.writeObject(hashmap_persona);
    			oos.flush();
    			oos.close();
    		} catch (Exception e) {
    			e.printStackTrace();
    		}
    	}
    	
    	public static void main(String[] args) {
    		new SalvaOggetti();
    	}
    }

  2. #2
    Perchè non posti lo stacktrace dell'errore completo?
    "Mai discutere con un idiota. Ti trascina al suo livello e ti batte con l'esperienza." (Oscar Wilde)

  3. #3
    Innanzitutto grazie per l'interessamento. Ecco lo stacktrace:

    codice:
    java.io.NotSerializableException: SalvaOggetti
    	at java.io.ObjectOutputStream.writeObject0(Unknown Source)
    	at java.io.ObjectOutputStream.defaultWriteFields(Unknown Source)
    	at java.io.ObjectOutputStream.writeSerialData(Unknown Source)
    	at java.io.ObjectOutputStream.writeOrdinaryObject(Unknown Source)
    	at java.io.ObjectOutputStream.writeObject0(Unknown Source)
    	at java.io.ObjectOutputStream.writeObject(Unknown Source)
    	at java.util.HashMap.writeObject(Unknown Source)
    	at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    	at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
    	at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
    	at java.lang.reflect.Method.invoke(Unknown Source)
    	at java.io.ObjectStreamClass.invokeWriteObject(Unknown Source)
    	at java.io.ObjectOutputStream.writeSerialData(Unknown Source)
    	at java.io.ObjectOutputStream.writeOrdinaryObject(Unknown Source)
    	at java.io.ObjectOutputStream.writeObject0(Unknown Source)
    	at java.io.ObjectOutputStream.writeObject(Unknown Source)
    	at SalvaOggetti.<init>(SalvaOggetti.java:33)
    	at SalvaOggetti.main(SalvaOggetti.java:42)

  4. #4
    Utente di HTML.it
    Registrato dal
    Aug 2002
    Messaggi
    8,013
    non ne sono interamente sicuro (indagherò su internet), ma credo che il problema si presenti perché nel momento in cui tu cerchi di serializzare l'HashMap (che implementa Serializable e quindi non dovrebbe generare problemi) contenente Persona (che giustamente è Serializable) a ritroso la JVM provi a serializzare la classe contenitore (Persona è inner) e SalvaOggetti non è Serializable. Ho appena fatto un tentativo a portare fuori Persona ed il tuo codice funziona alla perfezione:
    codice:
    class Persona implements Serializable {
    		String nome;
    		String cognome;
    		String indirizzo;
    		int età;
    
    		public Persona() {
    
    		}
    		public Persona(String nome, String cognome, String indirizzo, int età) {
    			this.nome = nome;
    			this.cognome = cognome;
    			this.indirizzo = indirizzo;
    			this.età = età;
    		}
    	}
    
    public class SalvaOggetti {
    	
    
    	HashMap<String, Persona> hashmap_persona = new HashMap<String, Persona>();
    	ObjectOutputStream oos;
    
    	public SalvaOggetti() {
    		hashmap_persona.put("Test_1", new Persona("Mario", "Rossi", "Casa sua", 30));
    
    		try {
    			oos = new ObjectOutputStream(new FileOutputStream("C:/Users/Andrea/Desktop/prova.txt"));
    			oos.writeObject(hashmap_persona);
    			oos.flush();
    			oos.close();
    		} catch (Exception e) {
    			e.printStackTrace();
    		}
    	}
    
    	public static void main(String[] args) {
    		new SalvaOggetti();
    	}
    }
    Edit: cosa che non avevo mai usato, static nested class. Dichiara nel tuo codice la classe Persona come
    codice:
    static class Persona { ...
    e funzionerà anche in quel modo.
    http://download.oracle.com/javase/tu...OO/nested.html
    <´¯)(¯`¤._)(¯`»ANDREA«´¯)(_.¤´¯)(¯`>
    "The answer to your question is: welcome to tomorrow"

  5. #5

    Re: [Java] ObjectOutputStream writeObject NotSerializableException

    Originariamente inviato da acqualol
    Devo salvare su file un hashmap che ha per chiave una String e per valore una classe personalizzata.
    Per fare correttamente e per bene le cose dovresti separare le operazioni di creazione e accesso in scrittura/lettura al file (nel quale salvare i dati), dalla classe che gestisce i dati (HashMap) run-time:

    1) dovresti incapsulare il tuo HashMap in una classe e dotarla di metodi per effettuare operazioni di accesso/modifica del tuo HashMap dall'esterno, in questa puoi definire l'inner-class Persona. (Ricorda che le due classi devono implementare Serializable).
    2) ti crei una classe che gestisce il file, che cioè consente di andare a caricare/salvare l'istanza della classe precedente.

    Per quanto riguarda la tua classe SalvaOggetti, non è consigliato istanziare oggetti ObjectOutputStream/ObjectInputStream direttamente nel costruttore.

  6. #6
    Come ha detto Andrea1979, aggiungendo static tutto funziona alla perfezione (mitico).
    Un grazie anche a VincenzoTheBest per i consigli.
    Questo problema mi bloccava da giorni, ora posso dormire tranquillo.
    Grazie mille!

  7. #7
    Utente di HTML.it
    Registrato dal
    Feb 2007
    Messaggi
    4,157
    inoltre mi domando perché non sfruttare a pieno i vantaggi della programmazione object oriented utilizzando un'unica classe e per quello che serve classi inner statiche.
    Capisco che non conosci a pieno la programmazione java, ma esiste un motivo particolare per cui crei un'unico mega blocco con Persona statica? oltretutto non dai elementi di protezione per l'accesso, né inserisci getter/setter....dall'esterno come usi questa persona? metti gli oggetti, ne crei istanze e poi cosa ci fai?

  8. #8
    Originariamente inviato da valia
    inoltre mi domando perché non sfruttare a pieno i vantaggi della programmazione object oriented
    Per la serie: cose fatte bene, no errori logici.
    Se avesse pensato bene di incapsulare l'HashMap non sarebbe mai caduto in quell'errore logico, in quanto avrebbe sicuramente serializzato anche SalvaOggetti.

  9. #9
    Per quanto riguarda elementi di protezione e metodi getter/setter li ho volutamente omessi per non appesantire il thread. Ho postato solo il punto del codice che mi creava il problema in modo da rendere più immediata la lettura e l'individuazione del problema.

    Per quanto riguarda lo stile, purtroppo come ho anticipato, sono ancora agli inizi e non so proprio come sia l'approccio classico.

    Avrei dovuto dichiarare la classe Persona in un file a parte? Ogni consiglio è ben accetto.

    Grazie.

  10. #10
    Originariamente inviato da acqualol
    Avrei dovuto dichiarare la classe Persona in un file a parte?
    Se deve essere utilizzata da altre classi si, altrimenti se deve essere utilizzata solo dalla classe in cui è stata definita allora la soluzione dell'inner-class è corretta.

Permessi di invio

  • Non puoi inserire discussioni
  • Non puoi inserire repliche
  • Non puoi inserire allegati
  • Non puoi modificare i tuoi messaggi
  •  
Powered by vBulletin® Version 4.2.1
Copyright © 2025 vBulletin Solutions, Inc. All rights reserved.