简体   繁体   English

序列化包含其他ArrayList对象的ArrayList对象的问题

[英]Issues Serializing an ArrayList object containing other ArrayList objects

So I'm Serializing an ArrayList of ArrayLists essentially but I'm running into an issue. 所以我本质上是序列化一个ArrayLists的ArrayList,但是我遇到了一个问题。 To be honest I'm still pretty new to Java, I've tried so many different methods to fix this as well as searched relentlessly on this site and have not been successful. 老实说,我对Java还是很陌生,我尝试了许多不同的方法来解决此问题,并在该站点上进行了不懈的搜索,但未成功。 I know that the way I word things may be hard to follow along or is confusing so I'll post my code here to see. 我知道我的措辞方式可能很难遵循或令人困惑,因此我将在此处发布代码以供参考。 Sorry in advance for all the code. 对不起,所有代码。 SuperUsers has an arraylist of LoginInfo, PasswordKeeper has an Arraylist of SuperUsers, and the SuperUser arraylist gets serialized in PasswordKeeper. SuperUsers具有LoginInfo的阵列列表,PasswordKeeper具有SuperUsers的阵列列表,并且SuperUser阵列列表在PasswordKeeper中进行序列化。 but any changes made to the LoginInfo arraylist do not save and i cannot figure out why. 但是对LoginInfo arraylist所做的任何更改都不会保存,并且我无法弄清楚原因。 If anyone can help I would really Appreciate it. 如果有人可以提供帮助,我将不胜感激。 Thanks 谢谢

public class PasswordKeeper{

    private ArrayList<SuperUser> users;
    private static Scanner keyboard = new Scanner(System.in);

    public PasswordKeeper() {
        users = new ArrayList();
    }

    public void login() {
        try {
            // reads in SuperUser arraylist
            get();
        } catch (EOFException a) {
            System.out.println("You are the First User!");
        } catch (IOException b) {
            System.out.println(b);
        } catch (ClassNotFoundException c) {
            System.out.println(c);
        }
        boolean loopDisplay = true;
        while (loopDisplay) {
                existingUser = keyboard.next();
                existingPass = keyboard.next();
                SuperUser temp = new SuperUser(existingUser, existingPass);
                System.out.println();
                if (users.contains(temp)) {

                    // viewing superUser method
                    temp.display();
                    //saves after method call is over
                    try {
                        System.out.println("Saving.");
                        save(users);
                    } catch (IOException e) {
                        System.out.println(e);
                    }
                }
            }
            //This happens if there is a new user
            if(answer == 2){
            SuperUser tempNew = null;
            boolean cont = true;
            String newUser;
            String pass;
            while(cont){
                newUser = keyboard.nextLine();
                System.out.println();
                //System.out.println(users.size());

                tempNew = new SuperUser(newUser, pass);
                if(passValid(pass) == true){
                    if(makeSure(tempNew) == true){
                        System.out.println("Login Created!");
                        tempNew = new SuperUser(newUser, pass);
                        //actually being added to the arraylist
                        users.add(tempNew);
                        cont = false;
                    }
                }
            }
            //SuperUser.display method
            tempNew.display();
            try{
                System.out.println("Saving.");
                save(users);    
            }catch(IOException e){
                System.out.println(e);
            }
        }
        }
    }
    //makeSure and passValid methods
    public boolean makeSure(SuperUser user){
    if(users.contains(user)){
        return false;
    }
    return true;    
}

public boolean passValid(String pass){
        boolean passes = false;
        String upper = "(.*[A-Z].*)";
        String lower = "(.*[a-z].*)";
        String numbers = "(.*[0-9].*)";
        String special = "(.*[,~,!,@,#,$,%,^,&,*,(,),-,_,=,+,[,{,],},|,;,:,<,>,/,?].*$)";

        if((pass.length()>15) || (pass.length() < 8)){
            System.out.println("Entry must contain over 8 characters\n" +
            "and less than 15.");
            passes = false;
        }if(!pass.matches(upper) || !pass.matches(lower)){
            System.out.println("Entry must contain at least one uppercase and lowercase");
            passes = false;
        }if(!pass.matches(numbers)){
                    System.out.println("Password should contain atleast one number.");
                    passes = false;
        }if(!pass.matches(special)){
                    System.out.println("Password should contain atleast one special character");
                    passes = false;
        }else{
            passes = true;
        }
        return passes;
    //serializable methods
    public void save(ArrayList<SuperUser> obj) throws IOException {

        File file = new File("userInformation.dat");
        FileOutputStream fileOut = new FileOutputStream(file, false);
        BufferedOutputStream buffedOutput = new BufferedOutputStream(fileOut);
        ObjectOutputStream out = new ObjectOutputStream(buffedOutput);
        out.writeObject(obj);
        out.close();
        fileOut.close();
    }

    public ArrayList<SuperUser> get() throws IOException, ClassNotFoundException {
        FileInputStream fileIn = new FileInputStream("userInformation.dat");
        BufferedInputStream buffedInput = new BufferedInputStream(fileIn);
        ObjectInputStream in = new ObjectInputStream(buffedInput);
        users = (ArrayList<SuperUser>) in.readObject();
        in.close();
        fileIn.close();
        return users;
    }

    public class SuperUser implements Serializable {
        private String userName;
        private String password;
        private static Scanner keyboard = new Scanner(System.in);
        private ArrayList<LoginInfo> info = new ArrayList();

        public SuperUser(String name, String pass) {
            userName = name;
            password = pass;
        }

        public String getUser() {
            return userName;
        }

        public void display() {

            String next = keyboard.next();
            //want to add data to LoginInfo arraylist
            if (next.equalsIgnoreCase("add")) {
                add();
            } else if (next.equalsIgnoreCase("delete")) {
                delete();
            } else if (numberCheck(next)) {
                int choice = (int) Integer.parseInt(next) - 1;
                edit(choice);
            //!!!! this: after doing this i lose whatever data i added
            //to the LoginInfo arraylist, right after this the
            //SuperUser arraylist gets saved. but the added data to 
            //loginInfo does not
            } else if (next.equalsIgnoreCase("logout")) {
                System.out.println(info.size());
            }
        }

        public boolean numberCheck(String in) {
            try {
                Integer.parseInt(in);
            } catch (NumberFormatException e) {
                return false;
            }
            return true;
        }
        //method to add to the Arraylist
        public void add() {
            System.out.println("What is the website name?:");
            String trash = keyboard.nextLine();
            String webName = keyboard.nextLine();
            System.out.println("The Username?:");
            String webUsername = keyboard.nextLine();
            System.out.println("The Password?:");
            String webPass = keyboard.nextLine();
            info.add(new LoginInfo(webUsername, webPass, webName));
            System.out.println(info.size());
            //method goes back to display
            display();
        }
    }
}

You have a list named users . 您有一个名为users的列表。 Once you created new SuperUser instance ( temp ), you are checking that it belongs to this list ( users.contains(temp) , which is false of course - from where it will occur there?). 一旦创建了新的SuperUser实例( temp ),便要检查它是否属于此列表( users.contains(temp) ,这当然是错误的-从哪里出现?)。 If it have belonged, the method display would be called, which in turn would add LoginInfo to that SuperUser ( add() call), but I bet in reality it doesn't happened. 如果属于该方法,则将调用方法display ,该方法随后会将LoginInfo添加到该SuperUseradd()调用)中,但我敢打赌,实际上并没有发生。

Also, I see where you read from users (check whether new SuperUser instances belong there), I see where you overwrite it (during desealization) but I don't see adding any instance to there, which makes me think that it is always empty. 此外,我看到您从users那里读取信息(检查是否有新的SuperUser实例属于该用户),我看到了您在哪里覆盖了它(在反渗透期间),但是我看不到在其中添加任何实例,这使我认为它始终为空。

Are you sure that SuperUser contains any LoginInfo in its array list? 您确定SuperUser在其数组列表中包含任何LoginInfo吗?

Your problem is here 你的问题在这里

SuperUser temp = new  SuperUser(existingUser, existingPass);
    System.out.println();
    if (users.contains(temp)) {
        // viewing superUser method
        temp.display();

You create a temporary object which with the username and password. 您创建一个使用用户名和密码的临时对象。

Your 'users.contains()' method returns true because '.equals()' is based on the username, however the 'temp' object is a different instance to that in the list. 您的'users.contains()'方法返回true,因为'.equals()'基于用户名,但是'temp'对象与列表中的实例不同。

So when you call 'temp.display()' it is not calling on an object in the list, so no data changes will save. 因此,当您调用“ temp.display()”时,它不会调用列表中的对象,因此不会保存任何数据更改。

You need to find the existing object from the list for that user. 您需要从列表中找到该用户的现有对象。 I would suggest that you swap your list for a map keyed on username. 我建议您将列表换成以用户名作为关键字的地图。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM