Как мы достигаем add (4) (10) (20) (3) (1) .total, используя функцию Java? - PullRequest
1 голос
/ 07 апреля 2019

Я изучаю использование,

java.util.function.Function

Я написал код, который использует функцию Java для добавления 4 к себе,

код выглядит следующим образом,

public class Test01 {

    public static void main(String[] args) {
        Function<Integer,Integer> addFunction = new Function<Integer,Integer>() {
            private int total = 0; 
            public Integer apply(Integer value) {               
                this.total += value; 
                return this.total;
            }
        };



        int finalTotal = addFunction.andThen(addFunction)
                                    .andThen(addFunction)
                                    .andThen(addFunction)
                                    .apply(4);

        System.out.println(finalTotal);
    }

}

Когда я запускаю приведенный выше код, я получаю вывод

32

Как мне добиться чего-то, что я сделал в javaScript, а именно:

var fn19 = function(){

        var addNum = function(num){

            var fn = function(num2){
                fn.sum += num2;             
                return fn;
            };

            fn.sum = num;   
            return fn;
        };

        print("addNum(3)(4)(3)(10) ==>  "+addNum(3)(4)(3)(10).sum); 
};

fn19();  

Выводприведенного выше кода:

addNum(3)(4)(3)(10) ==> 20

Могу ли я иметь такой же вызов функции Java, где я могу передать столько аргументов числа, и addFunction добавит эти много чисел.

Ответы [ 3 ]

1 голос
/ 08 апреля 2019

Примером, максимально приближенным к вашему коду JavaScript, будет

class QuestionableConstruct {
    int sum;
    QuestionableConstruct add(int num2) {
        sum += num2;
        return this;
    }
}
Runnable fn19 = () -> {
    IntFunction<QuestionableConstruct> addNum = num -> {
        QuestionableConstruct fn = new QuestionableConstruct();
        fn.sum = num;   
        return fn;
    };
    System.out.println("addNum(3)(4)(3)(10)==> "+addNum.apply(3).add(4).add(3).add(10).sum);
};
fn19.run();

Более Java-подобное решение будет

interface Add {
    int sum();
    default Add add(int num) {
        int sum = sum() + num;
        return () -> sum;
    }
    static Add num(int num) {
        return () -> num;
    }
}

пригодным для использования как

System.out.println("addNum(3)(4)(3)(10) ==>  "+Add.num(3).add(4).add(3).add(10).sum());

В отличие от конструкции JavaScript, здесь используются реальные неизменяемые функции.Рассмотрим

Add a = Add.num(1).add(2).add(3);
System.out.println("1+2+3+4+5 = "+a.add(4).add(5).sum());
System.out.println("1+2+3+10+20 = "+a.add(10).add(20).sum());

, который работает без помех.

Но, конечно, если вы просто хотите суммировать переменное количество элементов, используйте

System.out.println("addNum(3)(4)(3)(10) ==>  "+IntStream.of(3, 4, 3, 10).sum()); 

или еслиВы хотите изменчивый аккумулятор, используйте

System.out.println("addNum(3)(4)(3)(10) ==>  "+
    IntStream.builder().add(3).add(4).add(3).add(10).build().sum());

, который позволяет сохранить строителя и передать его.

0 голосов
/ 07 апреля 2019

Техника, которую вы описываете в мире JavaScript, использует замыкание.

Это хороший побочный эффект от функций в JavaScript, являющихся гражданами первого класса. Это способ связывания функций с данными во внешней области видимости, а затем возможность передавать эту связь без потери внутреннего контекста. Наиболее распространенное / простое использование которого - кэширование (его формальное название - памятка).

Вам бы понадобились функции (методы) в Java, чтобы быть первым классом, но это было бы избыточно, поскольку классы по замыслу являются сущностью, которая связывает данные и методы, что делает всю концепцию замыкания в этом контексте избыточной.

0 голосов
/ 07 апреля 2019

Вы не можете точно сделать это в Java, то, что вы ищете, это сокращение потока значений.

Другими словами: «реальное» функциональное решение здесь не в том, чтобы вызывать один метод с несколькими аргументами. Вместо этого у вас есть значения в каком-то списке, а затем вы определяете функцию, которая «накапливается» в содержимом этого списка, применяя функцию к элементам.

См. здесь для некоторых примеров.

...