简体   繁体   中英

Accessing subclass method from arraylist of superclass

For an assignment, I have an ArrayList of type "Reference". Reference is a parent class to the "Book" class and "Journal" class. If I am allowed to add objects of type "Book" and "Journal" to the Arraylist, why would I be getting an error if I want to access methods of Book and Journal via the following code?

          ArrayList.get([someindex]).someBookorJournalMethod()

The arraylist itself is of the parent class, and the methods I want to access are only defined for either book or either journal.

EDIT: Here is some code

  public class Books extends Reference{

   private String Authors;
   private String Publishers;


      public Books(String CallNum, String Author, String Title, String Publisher, int year,String type)
      {

          super(CallNum,Title,year,type);

          Authors= Author;
          Publishers=Publisher;
      }

public String getAuthor()
{
    return Authors;
}



 public class LibrarySearch {


      private ArrayList<Reference> Library;


      public LibrarySearch()
      {
          Library = new ArrayList<Reference>(100);
      }


      public outputLibrary(){

      for (int i = 0 ; i < Library.size(); i+++)
      {
        if (Library.get(i).getType().equals("Book"))
        {
            System.out.println("Type:book\n" + "Call Number:" +  Library.get(i).getCallNumber() +"\n" + "Authors:" + Library.get(i).getAuthors();)
        }
    }

}

IntelliJ is having issues with the line Library.get(i).getAuthors() because it is a method specific to Books. How would I resolve this?

Because when you specify the type of a variable, you can only invoke methods that are defined for this type. For example, if you have

public class A {
  public void methodA() {
    System.out.println("A");
  }
}

public class B extends A {
  public void methodB() {
    System.out.println("B");
  }
}

public class Main {
  public static void main(String[] args) {
    A ab = new B();
    ab.methodB();
  }
}

This will not compile, since the type defined for the variable ab is A and the only visible methods are those that are defined in A .

In your case you can simply add a blank method in Reference (if you don't want to make the class abstract):

public void someBookorJournalMethod() {}

Or you can explicitly cast the object you're trying to invoke the method for.

However, it is important to note that both approaches are usually bad practices and should be avoided. If it does not make sense to instantiate Reference objects, than make the class abstract and define someBookorJournalMethod as an abstract method. In your code you're most probably using inheritance in a wrong way.

You can't access the method of a subclass from the superclass. So you'll need to cast to a Book or a Journal.

Reference r =ArrayList.get([someindex]);
if (r instanceof Book) {
    ((Book) r).someBookMethod();
} else if (r instanceof Journal) {
     ((Journal) r).someJournalMethod();
} 

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

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