SAM(Single Abstract Method) 인 Interface 는 모두 Functional Interface 이라고 할 수 있습니다. 즉, 추상메소드를 딱 하나만 가지고 있는 인터페이스를 의미합니다. (Object 클래스로부터 상속 받은 메소드는 제외)
위 의 조건을 만족하는 인터페이스는 Functional Interface 로 인지되며, 람다 표현식에 적용이 가능합니다.
만약 Functional Interface 임을 명시적으로 알려야 할 필요가 있을 경우는 @FunctionalInterface 애노테이션을 사용하여 명시합니다.
@FunctionalInterface
public interface Blah {
void test();
...
}
파라미터 1개, 리턴 1개 형태의 apply() 형태의 SAM 표현입니다.
R apply(T t);
compose(), andThen() 으로 조합해서 사용 가능합니다.
Function<Integer, Integer> plus5 = (value) -> value + 5;
Function<Integer, Integer> mul2 = (value) -> value * 2;
System.out.println(plus5.compose(mul2).apply(3)); // (3 * 2) + 5
System.out.println(plus5.andThen(mul2).apply(3)); // (3 + 5) * 2
파라미터 2개, 리턴 1개 형태의 apply() 형태의 SAM 표현입니다.
R apply(T t, U t);
andThen 으로 Function<T, R> 조합 사용 가능합니다.
BiFunction<Integer, Integer, Integer> func1 = (val1, val2) -> val1 * val2;
Function<Integer, Integer> func2 = (val1) -> val1 + 1;
System.out.println( func1.apply(2, 3) ); // 6
System.out.println( func1.andThen(func2).apply(2, 3)); // 7
파라미터 1개, 리턴값은 없는 accept() 형태의 SAM 표현입니다.
파라미터를 전달받아 소비해버리는 이미지를 기억하면 좋습니다.
void accept(T t);
Consumer<String> supplier = (val) -> System.out.println("val : " + val);
supplier.accept("Jack"); // val : Jack
파라미터는 없고, 리턴값만 존재하는 get() 형태의 SAM 표현입니다.
무언가를 제공해주는 이미지를 기억하면 좋습니다.
T get();
import java.util.function.Supplier;
public class Foo {
private String name;
protected Foo() {}
public Foo(String name) {this.name = name; }
public String getName() {return this.name; }
public static void main(String[] args) {
Supplier<Foo> supplier = () -> new Foo("guest");
Foo foo = supplier.get();
System.out.println(foo.getName()); // guest
}
}
파라미터는 1개, 리턴값은 boolean. test() 형태의 SAM 표현입니다.
무언가의 판단(true/false) 의 근거가 되는 값을 판정(test) 해 주는 이미지를 기억하면 좋습니다.
boolean test(T t)
Predicate<Integer> pred1 = (n) -> n%2 == 0;
Predicate<Integer> pred2 = (n) -> n<10;
System.out.println(pred1.and(pred2).test(12)); // false
System.out.println(pred1.and(pred2).test(8)); // true
System.out.println(pred1.test(8)); // true
System.out.println(pred1.negate().test(8)); // false
그 외 BiFunction 에서의 모든 입,출력값 타입이 동일하다던가.. 등의
경우를 위해 여러가지 Functional Interface 를 제공하고있으며 해당 내용은 아래 링크 참조
https://docs.oracle.com/javase/specs/jls/se8/html/jls-9.html#jls-9.8
https://docs.oracle.com/javase/8/docs/api/java/util/function/package-summary.html