Last.fm java.lang.ClassCastException - reading in User objects from file

1.1k views Asked by At

I would really appreciate if anyone can help me with this issue. I'm getting an error when I run this class UniqueUsersData.java

Exception in thread "main" java.lang.ClassCastException: java.lang.String cannot be cast to java.util.HashSet
    at gettingData.UniqueUsersData.main(UniqueUsersData.java:30)

UniqueUsersData.java:

package gettingData;

import java.io.BufferedInputStream;
import java.io.BufferedWriter;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.FileWriter;
import java.io.IOException;
import java.io.InputStream;
import java.io.ObjectInput;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.util.ArrayList;
import java.util.HashSet;
import java.io.Serializable;

import de.umass.lastfm.User;

public class UniqueUsersData {

public static void main(String[] args) throws IOException, ClassNotFoundException{

    HashSet<User> userData = null;
    String fileName = "users.csv";
    ObjectInputStream in = new ObjectInputStream(new FileInputStream(fileName));

    try{
        while(in != null ){ // keep reading if there are more lines in the file
        userData = (HashSet<User>) in.readObject();
        }
    }catch(IOException e){
      e.printStackTrace();
    }

    String file = "usersInfo.csv";

    BufferedWriter out = new BufferedWriter(new FileWriter(file, true));

    for(User u: userData){
        System.out.println(u.getId() + "," +  u.getName() + "\n");
    }

    out.close();

} // end main method

} // end class

I have another class which gets the data using the last.fm api, stores User objects to an arraylist and then writes those objects to a file (users.csv). That all works fine, and I write to the file using an ObjectOutputStream.

I've read things about the class needing to be Serializable, but I'm assuming that de.umass.lastfm.User doesn't implement it.

Is there something I'm missing here?

Thanks for any help!

2

There are 2 answers

2
Kaushal On

You are getting an exception since data in file users.csv is stored as string whereas you are trying to convert (cast) it to HashSet . In general readObject() method returns an Object which can be casted to same data type which was serialized. Please check what object was added to file users.csv. Was it the ArrayList or something else.

Note: User objects cannot be stored in file if it is not Serializable, you would get java.io.NotSerializableException

Code below shows the sample User read and writes with some modification

User.java

package de.umass.lastfm;

import java.io.Serializable;

public class User implements Serializable{

private static final long serialVersionUID = 1L;

private String id;
private String name;
/**
 * @return the id
 */
public String getId() {
    return id;
}
/**
 * @param id the id to set
 */
public void setId(String id) {
    this.id = id;
}
/**
 * @return the name
 */
public String getName() {
    return name;
}
/**
 * @param name the name to set
 */
public void setName(String name) {
    this.name = name;
}
}

UniqueUsersData.java

package de.umass.lastfm;

import java.io.BufferedWriter;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.FileWriter;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.util.ArrayList;
import java.util.List;


public class UniqueUsersData {

public static void main(String[] args) throws IOException, ClassNotFoundException{

    //populating user object in arraylist STARTS
    User user1 = new User();
    user1.setId("1");
    user1.setName("name1");

    User user2 = new User();
    user2.setId("2");
    user2.setName("name2");

    List<User> userList = new ArrayList<User>();
    userList.add(user1);
    userList.add(user2);
    //populating user object in arraylist ENDS

    // Add ArrayList<User> to file users.csv STARTS
    try{

        FileOutputStream fout = new FileOutputStream("users.csv");
        ObjectOutputStream oos = new ObjectOutputStream(fout);   
        oos.writeObject(userList);
        oos.close();
        System.out.println("file added users.csv");

       }catch(Exception ex){
           ex.printStackTrace();
       }
    // Add ArrayList<User> to file users.csv ENDS

    // Reading ArrayList<User> from file users.csv STARTS
    ArrayList<User> userData = null;
    String fileName = "users.csv";
    ObjectInputStream in = new ObjectInputStream(new FileInputStream(fileName));

    try{
    userData = (ArrayList<User>) in.readObject();
    }catch(IOException e){
      e.printStackTrace();
    } finally {
    in.close();
    }

    String file = "usersInfo.csv";

    BufferedWriter out = new BufferedWriter(new FileWriter(file, true));

    for(User u: userData){
    System.out.println(u.getId() + "," +  u.getName() + "\n");
    }

    out.close();

} // end main method

} // end class
0
Abimaran Kugathasan On

in.readObject() returns a String, and you are casting to HashMap. That why you got ClassCastException. You may need write user details (user's field) in String format (may be comma separated values), then you can read them as a String, split with comma and assign them to user objects line by line.