2015-06-09 2 views
0

Я пытаюсь прочитать данные из файла, содержащего несколько объектов класса. Но я получаю исключение из null-указателя при добавлении объектов в список. может ли кто-нибудь помочь?чтение данных из сериализованного файла, содержащего несколько объектов

Вот код:

//I'm following the same approach, but getting null Pointer exception while 
//adding the object to a list. I'll post my code below. Can anyone help? 

public class DeserializingMultipleObjects { 

/** 
* @param args the command line arguments 
*/ 
public static void main(String[] args) throws IOException { 
    //create few objects of student class and serialize them in a single file 

    Student st1= new Student(1, "abhishek", 24, 1); 
    Student st2= new Student(2, "Prashant",23,3); 
    Student st3= new Student(3,"Gayatri",22,2); 
    Student st4= new Student(4,"Ankul",23,4); 

    FileOutputStream fout= null; 
    FileInputStream fin= null; 
    ObjectInputStream oin=null; 
    ObjectOutputStream oout= null; 
    List <Student> studentList=null; 

    try{ 
    fout= new FileOutputStream("Student.ser"); 
    oout= new ObjectOutputStream(fout); 
    oout.writeObject(st1); 
    oout.writeObject(st2); 
    oout.writeObject(st3); 
    oout.writeObject(st4); 

    //objects have been serialized. Now read them and populate in a list 

    fin= new FileInputStream("Student.ser"); 
    oin= new ObjectInputStream(fin); 
    boolean flag=false; 

    while(!flag){ 
     if(oin.readObject()==null || oin.readObject().equals("")){ 
     flag=true; 
     } 
     else{ 
     studentList.add((Student)oin.readObject()); 
     } 
    } 


    } 

    catch (ClassNotFoundException ex) { 
     Logger.getLogger(DeserializingMultipleObjects.class.getName()).log(Level.SEVERE, null, ex); 
    }  finally{ 
    if(fout !=null) try { 
     fout.close(); 
    } catch (IOException ex) { 
     Logger.getLogger(DeserializingMultipleObjects.class.getName()).log(Level.SEVERE, null, ex); 
    } 
    if(oout !=null){ 
    oout.close(); 
    } 
    if(fin !=null){ 
    fin.close(); 
    } 
    if(oin !=null){ 
    oin.close(); 
    } 

    for(Student student: studentList){ 

     System.out.println(student.name); 
    } 
    } 
} 

} 

ответ

0

List <Student> studentList=null; дает сведения об ошибке. Когда вы достигнете той части, которую хотите добавить в studentList, с номером studentList.add((Student)oin.readObject());, этот список является нулевым указателем, потому что вы его инициализировали как таковой.

Возможно, вы захотите инициализировать список чем-то другим, кроме нулевого, например. List<Student> studentList = new ArrayList<Student>();

+0

@JB Nizet и blueygh2, спасибо за помощь guyz. Глупые ошибки сделали код хуже. Однако получил что-то новое, чтобы учиться. Код работал нормально после нескольких изменений. –

1

Читаешь ваш объект в три раза на одну итерацию.

while(!flag){ 
    Student st = oin.readObject(); 
    if(st == null){ 
     flag=true; 
    } 
    else{ 
     studentList.add(st); 
    } 
} 
0

Несколько ошибок:

  1. Вы забыли закрыть ObjectOutputStream перед тем начать читать из файла
  2. Каждый раз, когда вы звоните readObject(), вы прочитали следующий объект из потока, таким образом, следующие строки:

    if(oin.readObject()==null || oin.readObject().equals("")){ 
        flag=true; 
    } 
    else{ 
        studentList.add((Student)oin.readObject()); 
    } 
    

читать 2 или три объекта, вместо того, чтобы читать только один. Они должны быть

Object read = oin.readObject() 
    if(read == null || read.equals("")){ 
     flag=true; 
    } 
    else { 
     studentList.add((Student) read); 
    } 

Но readObject() никогда не будет возвращать нуль, и нет никакого способа, он возвращает пустую строку, так как вы только письменные экземпляры студента в потоке.

Все будет намного проще, если вы просто сохранили своих 4 студентов в List<Student> и засекретили этот список. Дезериализация просто заключалась бы в чтении одного объекта (так что никакой петли не требуется): список учеников.

Также, закрытие объекта ObjectOutputStream автоматически закрывает FileOutputStream. То же самое для ObjectInputStream. Поэтому закрытие потоков файлов не требуется. Для более чистой и безопасной обработки ресурсов вы должны использовать try-with-resources.

+0

и blueygh2, спасибо за помощь guyz. Глупые ошибки сделали код хуже. Однако получил что-то новое, чтобы учиться. Код работал нормально после нескольких изменений. - –

Смежные вопросы