오늘 입학식 웰컴 키트를 받았다.
선물 받은 기분이다.
함수적 프로그래밍 형태로 재사용 가능한 코드 블럭
Arrays.sort(ba, new Comparator<Book>() {
@Override
public int compare(Book o1, Book o2) {
return o1.title.compareTo(o2.title);
}
});
Arrays.sort(ba, (o1, o2) -> o1.title.compareTo(o2.title));
위 코드는 모두 title로 오름차순 하는 정렬 코드다.
위에는 익명 inner class를 이용한 정렬, 아래는 람다식을 이용한 정렬.
Lambda 식이 할당되는 인터페이스를 Lambda 식의 타겟 타입이라고 함.
타겟 타입은 반드시 abstract 메서드가 하나만 존재해야 함.
-> 이 메서드의 구현부가 Lambda로 대체됨.
그리고 이게 제대로 동작할 수 있는 지 컴파일 단계에서 확인 시켜주는 좋은 친구가 있다.
@FunctionalInterface
인터페이스에 이 어노테이션을 입력하면 Lambda식으로 표현할 수 있는지 알려준다.
@FunctionalInterface
interface MyFunctional1 {
void sayHello(String name);
void sayHi(); // abstract method가 두개라서 Lambda식으로 구현 불가. 즉, 컴파일 에러 뜸 (@FunctionalInterface 로 인해)
}
() -> {}
이런 형태를 갖으며,
() 안에는 변수, {} 안에는 구현부가 들어간다.
(String name) -> {System.out.println("Hello " + name);}
으로 사용할 수 있다.
하지만 귀찮음이 큰 우리 개발자는 극한의 효율을 더욱더 원하게 되는데,
(name) -> {System.out.println("Hello " + name);}
이런 식으로 타입도 없애고,
name -> System.out.println("Hello " + name);
이렇게 변수와 메서드가 각 하나일 경우, ()와ㅕ {}까지 없애버린다.
극한의 다이어트!
심지어 return만 필요한 코드일 경우, return 까지 생략할 수 있다...
Lambda 식 내부에서 this를 사용할 수 있다.this.뭐시기
하지만 헷갈릴 수 있는 부분이 있는데
Lambda 식에 작성한 this는 외부 클래스의 instance를 뜻한다.
또한,
외부 메서드의 local 변수는 읽기 전용이다.
이 표에 나온 종류들은 자주 사용되는 함수적 표준 API를 java.util.function 패키지에 있는 것들이다.
stream : 개울, 흐름
이라는 뜻을 갖는 것처럼 사용했을 때 말하는 것과 같은 코드를 작성할 수 있다.
Java8부터 추가된 java.util.stream 패키지에서 사용 가능하다.
배열 및 Collection의 요소르 하나씩 참조해서 처리하는 목적으로 사용된다.
컬렉션, 배열 등 데이터 소스에 대한 공통된 접근 방식을 제공해 준다.
Stream은 stream()
대신 parallelSream()
을 사용하여 병렬 처리도 가능하다는 특징이 있다.
내부 동작에 대해 자세하게 다루진 않겠지만, 분할 정복으로 다룬다고 생각하면 된다.