(Java) Использование функционального (предикатного) интерфейса, который выводит логическое значение из двоичного дерева - PullRequest
0 голосов
/ 19 января 2019

У меня небольшая проблема: я создал класс Binary Tree с некоторыми функциями, которые не интересны для этой задачи.Каждый узел хранит левого и правого потомка плюс родителя.Каждый узел имеет значение ключа, которое можно рассматривать как метку.Я создал 3 класса:

Tree.java - это класс узла.

BinaryTree.java содержит некоторые методы, относящиеся ко всему дереву, такие как значение min / max.

Main.java, который проверяет возможности дерева и содержит метод main.

МОЯ ПРОБЛЕМА: Я хотел написать функциональный интерфейс с методом, который получает узел в качестве параметра и выводитлогическое значение.Это может быть использовано для передачи корневого узла и повторной проверки, является ли каждый узел в дереве больше или меньше значения.Однако я совершенно новичок в функциональных интерфейсах и не могу понять логику функциональности.Это то, что я получил до сих пор:

@ FunctionalInterface

public interface NodeOperation {
    public abstract boolean forAll(Tree node);
}

NodeOperation overTwenty = (node) -> node.getValue() < 20;

Когда я пытаюсь использовать лямбда-нотацию, она не возвращает мне логическое значение, когда я хочу напечатать overTwenty.Может кто-нибудь помочь мне реализовать функциональный интерфейс и объяснить, как я получаю доступ к логической переменной, чтобы я мог начать думать о том, как я делаю это рекурсивно для каждого узла.

Если вы не знаете много о двоичных деревьях, я предлагаючтобы посмотреть это в Википедии.В моем случае я создал BST (дерево двоичного поиска), означающее, что его структура основана на больших значениях справа и меньших значениях слева.Если вам нужна какая-то конкретная часть моего кода, просто предложите это, и я опубликую это здесь:)

Ответы [ 2 ]

0 голосов
/ 19 января 2019

В java методы интерфейсов всегда общедоступны. Таким образом, ваш интерфейс может стать

@FuctionalInterface
    public interface NodeOperation {
        boolean forAll(Tree node);
    }

Итак, вы написали эту строку кода

NodeOperation overTwenty = (node) -> node.getValue() < 20;

который создает вам экземпляр интерфейса, который проверяет, является ли значение узла меньше 20

Итак, предположим, что у вас есть экземпляр узла Tree со значением 30 Если вы позвоните

 overTwenty.forAll(node) //will return false

Эта функция не является рекурсивной. Если вы хотите применить функцию ко всем дочерним узлам узла, вы должны написать рекурсивный метод для класса Tree

   public class Tree{
       ... 
    public boolean recursiveNodeOperation(NodeOperation operation) {
       if(!operation.forAll(this)) return false;
       for(Tree child : children) 
            if(! child.recursiveNodeOperation(operation)) 
                return false
       return true ;

      } 
    } 



root.recursiveNodeOperation(overTwenty); //will return true if all the nodes of the Tree starting from root are lower than 20

Этот метод рекурсивно применяет операцию Node, поэтому проверяет, что все элементы в Дереве соответствуют вашей функции

0 голосов
/ 19 января 2019

Объект overTwenty, который вы создали, является функцией. Если вы хотите использовать его в узле вашего дерева, вы должны вызвать его единственный метод в узле вашего дерева. Например, вы можете назвать это так:

boolean result = overTwenty.forAll(root);

Кстати, ваш NodeOperation интерфейс вполне эквивалентен Function<Tree, Boolean> с той небольшой разницей, что он возвращает примитив boolean вместо класса Boolean.

...