어떤 때 쓰는 걸까?
interface인데 Abstract Method가 딱 1개 있는 경우
Abstract Method가 1개인게 왜 중요할까요? Abstract Method가 1개이면 interface를 구현하는 class를 직접 만들지 않고 여러 간결한 문법들을 써서 변수에 interface를 구현하는 값을 바로 할당할 수 있기 때문입니다. 예를 들면...
- Lambda 식
- Method Reference
실제로 유용한 예시는 아니지만 String을 조작하기 위해 interface를 만든다고 해 보겠습니다.
@FunctionalInterface
interface StringTransformer {
String transform(String input);
}
🐜 Lambda 식
@FunctionalInterface가 있기 때문에 Interface를 구현하는 class를 만들지 않고 바로 Lambda 식을 할당할 수 있습니다.
StringTransformer toUpperCase = input -> input.toUpperCase();
🐜 Method Reference
비슷하게 Method Reference를 써서 바로 할당할 수 있습니다.
StringTransformer toUpperCase = String::toUpperCase;
@FunctionalInterface가 아닌데 쓰면 어떻게 될까?
Compile Error
@FunctionalInterface는 실제로 유용할까?
솔직히 잘 쓰이지는 않습니다. 제가 현업에서 구른 1년 6개월 동안 코드에서는 1번도 보지 못했고, Spring 코드를 까면서 보기 시작한 최근 몇 개월에 많이 보게 됐습니다. 하지만 @FunctionalInterface를 직접 만들지는 않더라도 간접적으로 쓰는 경우는 많습니다.
🐜 JDBC의 RowMapper
List<User> users = jdbcTemplate.query(
"SELECT * FROM users",
(rs, rowNum) -> new User(rs.getInt("id"), rs.getString("name"))
);
2번째 Argument를 보면 생각없이 썼지만 RowMapper interface를 구현하는 건데 새로운 Class를 만들지 않고 바로 Lambda로 만들고 있습니다. @FunctionalInterface입니다!
🐜 Spring Boot의 ApplicationRunner, CommandLineRunner
@Bean
public ApplicationRunner initRunner() {
return args -> System.out.println("Application started!");
}
비슷하게 Application Runner도 분명 interface인데 새로운 class를 만들어서 구현하는 게 아니라 바로 Lambda를 넘겨주고 있습니다. @FunctionalInterface가 없었다면 불가능한 일입니다.
package org.springframework.boot;
@FunctionalInterface
public interface CommandLineRunner {
void run(String... args) throws Exception;
}
🐜 Spring MVC의 HandlerInterceptor
HandlerInterceptor loggingInterceptor = (request, response, handler) -> {
System.out.println("Request received: " + request.getRequestURI());
return true;
};
Kotlin에서는 어떻게 사용될까?
Kotlin에도 비슷한 개념이 있습니다. 문법은 조금 다르지만요...
fun interface IntPredicate {
fun accept(i: Int): Boolean
}
위와 같이 fun interface를 쓰면 이걸 Function Interface라고 지정할 수 있습니다. 그럼 아래와 같이 하는 게 아니라...
val isEven = object : IntPredicate {
override fun accept(i: Int): Boolean {
return i % 2 == 0
}
}
더 간편하게 아래와 같이 할 수 있습니다!
val isEven = IntPredicate { it % 2 == 0 }
Functional (SAM) interfaces | Kotlin
kotlinlang.org
참고
FunctionalInterface (Java Platform SE 8 )
An informative annotation type used to indicate that an interface type declaration is intended to be a functional interface as defined by the Java Language Specification. Conceptually, a functional interface has exactly one abstract method. Since default m
docs.oracle.com
'👨💻 프로그래밍 > 📦 Backend' 카테고리의 다른 글
Gradle 기반 프로젝트에 Ktlint 적용하기 (3) | 2025.02.15 |
---|---|
(Spring 위주로) AOP 용어 정리 (0) | 2025.01.26 |
MDC로 풍부한 로그 쉽게 남기기 (0) | 2025.01.12 |
🥒 피클 (PKL): 새로운 설정 관리 언어 알아보기 (0) | 2024.11.02 |
Kotlin의 @JvmStatic 알아보기 (0) | 2024.08.12 |