Начните с «применить посетителя к узлу и всем его подузлам», то есть:
private void inOrder(Consumer<E> visitor, BinaryTreeNode<E> node) {
if (node != null) { // some stop condition
// TODO traverse left subnode
// TODO visit actual element
// TODO traverse right subnode
}
}
, и это называется как:
@Override
public void traverseInOrder(Consumer<E> visitor) {
inOrder(visitor, root);
}
, что, в свою очередь, можно назвать так:
traverseInOrder(e -> System.out.println(e));
// or, same as above
traverseInOrder(System.out::println);
Первый метод должен быть очень простым, например:
private void inOrder(Consumer<E> visitor, BinaryTreeNode<E> node) {
if (node != null) {
inOrder(visitor, t.left);
visitor.apply(t.element);
inOrder(visitor, t.right);
}
}
свободно на основе кода, размещенного в вопросе, предполагаемые типы, не проверенные
Примечание 1: при использовании класса java.util.function.Consumer
оно должно быть visitor.accept(t.element)
Примечание 2: как прокомментировано Clashsoft , правильный способ объявить visitor
(оба метода) будет выглядеть как Consumer<? super E> visitor
. Это означает, что посетитель является функцией, которая принимает аргумент типа E
или любой супертип типа E
(например, Consumer<Object>
, если E
является Integer
)