Подскажите, пожалуйста, как работает переопределенный метод toString() в задаче. Саму задачу решил, а один момент не могу понять
public static void main(String[] args) {
    List<Book> books = new LinkedList<Book>();
    books.add(new MarkTwainBook("Tom Sawyer"));
    books.add(new AgathaChristieBook("Hercule Poirot"));
    System.out.println(books);
}
1) Объявляем лист 4) Создаем объекты 3) добавляем элементы в лист 4) выводим в консоль лист, который выдаст массив внутри листа В родительском классе имеется метод getOutputByBookType(), который возвращает строку (как он работает понятно). toString() возвращает этот метод , то есть сначала вызывает, а потом возвращает его значение С этим пока вопросов нет. Вопрос вот в чем: метод toString() получается переопределен, хоть в исходном коде не указана аннотация @Override, но когда и где вызывается этот метод? Могу предположить, что он вызывается вот на этой строчке System.out.println(books); , а именно вот здесь - books , то есть тогда, когда выводим список листа. Если не ошибаюсь внутри листа имеется метод toString() . То есть мы переопределили в родительском классе именно этот метод? Скорее всего, да, потому что ,если удалить переопределенный метод toString(), то выводится хэш-код в шестнадцатеричном виде. Просто столкнулся с таким неявным вызовом переопределенного метода toString() впервые *задачу не удалю, помогите, пожалуйста, буду очень признателен