2016-04-19 3 views
0

У меня есть лямбдаОбъединение lambdas в Java?

(a, b) -> { 
    a.doSomething(); 
    a.doAnotherThing(); 
    return b.doSomething(); 
} 

Прямо сейчас, это просто привыкает в качестве параметра в одном методе. Тем не менее, я хотел бы также создать аналогичную лямбда

(a) -> { 
    a.doSomething(); 
    a.doAnotherThing(); 
    return a 
} 

Есть ли способ, которым я мог бы повторно использовать мой код? Что-то вроде

(a, b) -> { 
    partial(a) 
    return b.doSomething(); 
} 

(a) -> { 
    partial(a) 
    return a; 
} 
+1

Несомненно. Что тебя останавливает? –

+0

... Я не знаю как? Я не знаю, как выглядит правильный код: – Andrew

+0

Он будет выглядеть точно так же, как вы уже предложили. Просто напишите метод 'partial (a)'. –

ответ

0

Если я правильно понял, вы хотите позвонить лямбда из другой лямбда?

Вы могли бы дать им имя и использовать их, как и любой другой функции

Function<X,Y> partial = (a) -> { 
    a.doSomething(); 
    a.doAnotherThing(); 
    return a; 
} 

BiFunction<X,Y,Z> lam = (a, b) -> { 
    partial.apply(a); 
    return b.doSomething(); 
} 
+0

Тип 'lam' должен be 'BiFunction '. – saka1029

+0

Упс, спасибо! отредактировано –

+0

'partial (a)' -> 'partial.apply (a)'. – saka1029

0

Я предполагаю, что использование partial здесь не относится к функциональной концепции программирования частичных функций.

Рассматривая ваши примеры, операции с a взятые вместе являются только Потребителем, так как они не возвращают никаких значений. Ваша многоразовая лямбда может быть объявлена ​​как это:

Consumer<A> partial = a -> { 
    a.doSomething(); 
    a.doAnotherThing(); 
} 

Чтобы создать функцию, которая первый вызывает потребитель, вы можете сохранить этот помощник под рукой:

static <T,U,R> BiFunction<T,U,R> acceptAndThen(Consumer<T> c, Function<U,R> f){ 
    return (t,u) -> { 
     c.accept(t); 
     return f.apply(u); 
    }; 
} 

, которые вы могли бы использовать, чтобы составить функцию, эквивалентный исходная функция, как это (я не знаю, b.doSomething() «s тип возврата, я буду считать, C):

BiFunction<A,B,C> f1 = acceptAndThen(partial, B::doSomething); // equivalent to (a, b) -> { partial.accept(a); return b.doSomething(); } 

Ваш второй пример, который показывает, как можно повторно использовать partial иначе, выиграют от другого помощника, который преобразует Consumer<T> к Function<T,T>, возвращая T что Consumer<T> прооперировал:

static <T> Function<T,T> returnSelf(Consumer<T> consumer){ 
    return t -> { 
     consumer.accept(t); 
     return t; 
    }; 
} 

Таким образом, вы можете создать свой второй пример, как это:

Function<A,A> f2 = returnSelf(partial); // equivalent to (a) -> { partial.accept(a); return a; } 

Эти композиции не входят в стандартную библиотеку, но вы обнаружите, что такие интерфейсы, как Consumer и Function, имеют встроенные функции для компоновки существующих функциональных типов в новые. Например, Consumer имеет функцию andThen, которая может вызывать последовательные вызовы потребителей. Использование частичного изображения может отличаться

Consumer<A> partial = ((Consumer<A>) A::doSomething).andThen(A::doAnotherThing); 
Смежные вопросы