LambdaMetafactory — 람다 표현식과 메서드 참조를 위한 메타팩토리

LambdaMetafactory — 람다 표현식과 메서드 참조를 위한 메타팩토리

LambdaMetafactory단순한 "함수 객체(function object)"의 생성을 돕는 메서드들을 제공하는 클래스예요. 이 함수 객체는 제공된 MethodHandle에 위임함으로써 하나 이상의 인터페이스를 구현하는데, 필요하다면 타입 적응(type adaptation)과 인자의 부분 평가(partial evaluation)를 거쳐요. 이 메서드들은 보통 invokedynamic 콜 사이트의 부트스트랩 메서드로 사용되어, 자바 언어의 람다 표현식메서드 참조 표현식 기능을 지원해요.

출처: Java API Reference

본문

제공된 MethodHandle이 지정하는 동작에 대한 간접 접근은 세 단계를 순서대로 거쳐 진행돼요.

  1. 링크(Linkage): 이 클래스의 메서드들이 호출되는 시점이에요. 구현할 인터페이스(보통 단일 추상 메서드를 가진 함수형 인터페이스), 그 인터페이스에서 구현할 메서드의 이름·시그니처, 그 메서드에 대한 원하는 구현 동작을 설명하는 직접 메서드 핸들, 그리고 기타 추가 메타데이터를 인자로 받아, 적절한 함수 객체를 만들 수 있는 타깃을 가진 CallSite를 생성해요. 링크는 대상 인터페이스를 구현하는 새 클래스를 동적으로 로드하거나, 적절한 기존 클래스를 재사용할 수 있어요. CallSite는 함수 객체의 "팩토리"로 볼 수 있어서, 이 링크 메서드들을 "메타팩토리(metafactory)"라고 불러요.
  2. 캡처(Capture): CallSite의 타깃이 호출되는 시점이에요. 보통 invokedynamic 콜 사이트를 통해 함수 객체를 생성해요. 단일 팩토리 콜 사이트에 대해 여러 번 발생할 수 있어요. 동작 MethodHandle이 지정된 인터페이스 메서드의 파라미터보다 추가 파라미터를 가지면, 이들을 캡처된 파라미터(captured parameters) 라고 부르는데, CallSite 타깃에 인자로 제공해야 해요. 캡처된 파라미터의 예상 개수·타입은 링크 중에 결정돼요. 캡처는 새 함수 객체를 할당하거나 적절한 기존 함수 객체를 반환할 수 있어요. 캡처로 생성된 함수 객체의 정체성은 예측할 수 없어서, 참조 동등성·객체 잠금·System.identityHashCode() 같은 정체성 민감 연산은 구현에 따라 다르게 동작할 수 있어요.
  3. 호출(Invocation): 생성된 함수 객체의 인터페이스 메서드가 호출되는 시점이에요. 이때 캡처 시점에 바인딩된 인자들이 특정 호출마다 다를 수 있는 인자들과 함께 합쳐져, 동작 MethodHandle에 전달돼요.

자바 1.8부터 제공되는 final 클래스예요.

더 알아보기 (Learn more)