【问题标题】:NullPointerException when trying to get input for a serializable object尝试获取可序列化对象的输入时出现 NullPointerException
【发布时间】:2012-11-11 05:41:16
【问题描述】:

我有 3 个类:Main、ContactLibrary 和 ContactInfo。 ContactLibrary 包含一个名为 myPhoneBook 的 ArrayList。 ContactInfo 由一堆字符串组成,包含姓名、地址等。

例如,用户想要搜索姓名或任何涉及输入的内容。输入是在 ContactLibrary 和 ContactInfo 类中完成的——都是可序列化的对象。

然而,当它到达那个点时,我得到一个 NPE 错误。

You have 3 entry(s) saved to disc.

Hello, and welcome to Team 6's contact list.
What would you like to do?
Enter the corresponding number of choice.

1: Add an entry to the contact list.
2: Print the entire contact list.
3: Search for a contact.
4: Exit the program.

Please enter a number from 1-4.
3
What would you like to search by?
Exception in thread "main" java.lang.NullPointerException
    at ContactLibrary.searchByCriteria(ContactLibrary.java:62)
    at Main.optionsPrompt(Main.java:62)
    at Main.main(Main.java:25)
1: Last Names.
2: Emails.
3: Zip codes.

我该怎么办?

这是我的 Main:http://ideone.com/uvfK4U(包含顶级 cmets 中的其他两个类) 这是一个 UML 图:http://imgur.com/9W3TS

ContactLibrary 类,根据要求:

/**
 * ContactLibrary, when constructed, creates an ArrayList of ContactLibrary
 * references called myPhoneBook. Every index is made to fill in objects
 * of ContactInfo, which contains entries and credentials.
 * 
 * Contains methods to create a new entry, search and print by criteria, and print list.
 */
import java.util.*;

public class ContactLibrary implements java.io.Serializable {
    private static final long serialVersionUID = 1L;
    private ArrayList<ContactInfo> myPhoneBook;
    private Scanner libraryInput = new Scanner(System.in);

    /** Constructs the ArrayList that will hold references to ContactInfo. */
    public ContactLibrary() {
        myPhoneBook = new ArrayList<ContactInfo>();
    }

    /**
     * Adds an entry to the ArrayList and utilizes the set methods in
     * ContactInfo.
     */
    public void addEntry() {
        int doAgain = 1;
        do {
            myPhoneBook.add(new ContactInfo());
            System.out.println("Would you like to enter another contact?");
            System.out.println("1: Yes.");
            System.out.println("2: No.");
            doAgain = libraryInput.nextInt();
        } while (doAgain == 1);
    }

    /**
     * Goes through every index in myPhoneBook and runs ArrayList.get() on them.
     */
    public void printList() {
        for (int i = 0; i < myPhoneBook.size(); i++) {
            System.out.println(myPhoneBook.get(i));
        }
    }

    /** Counts the number of objects within myPhoneBook and returns a string. */
    public String scanDisc() {
        int entryCount = myPhoneBook.size();
        return "You have " + entryCount + " entry(s) saved to disc.\n";
    }

    /**
     * The prompt for having the user search the database via criteria. Asks the
     * user to enter in their search criteria.
     */
    public void searchByCriteria() {
        String criteria;
        //libraryInput = new Scanner("System.in");
        int subSubMenuChoice = 0;
        System.out.println("What would you like to search by?");
        System.out.println("1: Last Names.");
        System.out.println("2: Emails.");
        System.out.println("3: Zip codes.");
        subSubMenuChoice = libraryInput.nextInt();
        switch (subSubMenuChoice) {
        case 1:
            System.out
                    .println("Please enter the last name you'd like to search for:");
            criteria = libraryInput.next();
            searchByLastName(criteria);
            break;
        case 2:
            System.out
                    .println("Please enter the e-mail you'd like to search for:");
            criteria = libraryInput.next();
            searchByEmail(criteria);
            break;
        case 3:
            System.out
                    .println("Please enter the zip code you'd like to search for:");
            criteria = libraryInput.next();
            searchByZip(criteria);
            break;
        default:
            System.out.println("Exiting");
            break;
        }
    }

    /**
     * Loops through every element in the array and returns a toString of that
     * index for comparing with the search criteria via contains().
     */
    public void searchByEmail(String criteria) {
        for (int i = 0; i < myPhoneBook.size(); i++) {
            if (criteria.compareTo((myPhoneBook.get(i)).getEmail()) == 0) {
                System.out.println(myPhoneBook.get(i));
            } else {
                System.out.print("");
            }
        }
    }

    /**
     * Loops through every element in the array and returns a toString of that
     * index for comparing with the search criteria via contains().
     */
    public void searchByLastName(String criteria) {
        for (int i = 0; i < myPhoneBook.size(); i++) {
            if (criteria.compareTo((myPhoneBook.get(i)).getLastName()) == 0) {
                System.out.println(myPhoneBook.get(i));
            } else {
                System.out.print("");
            }
        }
    }

    /**
     * Loops through every element in the array and returns a toString of that
     * index for comparing with the search criteria via contains().
     */
    public void searchByZip(String criteria) {
        for (int i = 0; i < myPhoneBook.size(); i++) {
            if (criteria.compareTo((myPhoneBook.get(i)).getZipcode()) == 0) {
                System.out.println(myPhoneBook.get(i));
            } else {
                System.out.print("");
            }
        }
    }

    /** Reorganizes the array in order by last name. */
    public void sortData() {
        Collections.sort(myPhoneBook);
    }

}

【问题讨论】:

  • 请在方法searchByCriteria()中贴出类的代码:ContactLibrary,因为空指针在那里...
  • ContactLibrary.searchByCriteria(ContactLibrary.java:62) 在 Main.optionsPrompt(Main.java:62) 在 Main.main(Main.java: 25) 这不是堆栈跟踪吗?

标签: java nullpointerexception java.util.scanner serializable transient


【解决方案1】:

您在同一个 inputStream 上创建多个 Scanner 对象,最好只创建一个并将其传递给使用的方法或该类的构造函数中的下一个类。

在同一流上使用多个扫描仪。扫描器可以(并且将)消耗流——这可能(将)导致意想不到的副作用。最好不要这样做。

您可以将主类中的第 65 行替换为:

myLibrary.searchByCriteria(menuInput);

删除该行:(在您的类 ContactLibrary 中)

private Scanner libraryInput = new Scanner(System.in);

【讨论】:

  • 所以你的意思是我应该只在 Main 类中使用一台扫描仪...我该如何处理其他两个类?创建本地扫描仪?
  • 啊!我现在明白了。我的方法必须包含一个 Scanner 参数来捕获它,然后我可以在方法本身中使用它。非常感谢!
  • 好了。感恩节快乐!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2015-10-06
  • 2018-04-18
  • 2020-07-19
  • 2013-08-10
  • 1970-01-01
  • 1970-01-01
  • 2017-08-08
相关资源
最近更新 更多