[Java] 람다식
람다식 사용법
1) 람다함수란?
람다 함수는 익명 함수를 지정하는 용어이다. 즉 이름이 없는 함수로 이는 일급 객체라는 특징을 가지고 있다.
일급 객체란 일반적으로 다들 객체들에 적용 가능한 연산을 모두 지원하느 객체를 가르킨다. 함수를 값으로 사용 할 수도 있으며 파라미터로 전달 및 변수에 대입 하기와 같은 연산들이 가능하다.
2) 람다의 표현식
람다는 매개 변수 화살표 (->) 를 함수 몸체로 이용하여 사용 할 수 있다.
함수 몸체가 단일 실행문이면 괄호를 생략 할 수 있다. 하지만 함수 몸체가 return 문으로만 구성되어 있을 경우 괄호를 생략 할 수 없다.
ex)
void printVal(String name, int i) {
System.out.rpintnl(name +"=" + i);
}
위 메소드를 아래와 같이 변환할 수 있다.
(name , i) -> System.out.println(name+"="+i)
ex2)
int sumArr(int[] arr){
int sum=0;
for(int i: arr){
sum+=i;
}
return sum;
}
//람다식으로 변환
(int[] arr) -> {
int sum=0;
for(int i: arr) {
sum+=i;
}
return sum;
}
함수형 인터페이스
1) 함수형 인터페이스란?
함수형 인터페이스는 추상 메소드가 오직 하나인 인터페이스를 의미한다.
추상 메소드가 하나라는 뜻은 default method 또는 static method 는 여러 개 존재해도 상관 없다는 뜻이다.
그리고 @FunctionalInterface 어노테이션을 사용하는데, 이 어노테이션은 해당 인터페이스가 함수형 인터페이스 조건에 맞는지 검사해준다. 이는 없어도 괜찮지만 인터페이스 검증과 유지보수를 위해 붙여주는 편이 좋다.
2) 함수형 인터페이스 만들기
@FunctionalInterface
interface CustomInterface<T> {
// abstract method 오직 하나
T myCall();
//default method 는 존재해도 상관없음
default void printDefault() {
System.out.println("Hello Default");
}
//static method 는 존재해도 상관없음
static void printStatic() {
System.out.println("hello static");
}
}
이러한 함수형 인터페이스를 람다식으로 표현할 수 있다.
아래는 람다식으로 함수형 인터페이스를 표현한 것이다.
CustomInterface<String> customInterface = () -> "Hello custom";
//abstract method
String s = customInterface.myCall();
System.out.println(s);
//default method
customInterface.printDefault();
//static method
CustomFunctionalInterface.printStatic();
Variable Capture
지역 변수들을 미리 복사해서 가지고 있는 것을 Variable Capture라고 한다.
지역 변수를 캡처링하기 위한 2가지 제약 조건
a. 지역변수는 final 로 선언되어야 한다.
b. final로 선언되어 있지 않다면 final 처럼 동작해야 한다. 즉 값이 변경될 수 없다.
메소드, 생성자 레퍼런스
메소드 레퍼런스는 람다식에서 불필요한 매개변수를 제거할 떄 주로 사용한다. 즉 람다식으로 더욱 간단해진 익명 객체를 보다 더 간단하게 사용할 수 있도록 한다.
이는 람다식과 마찬가지로 인터페이스의 익명 구현 객체로 생성된다.
인터페이스의 추상 메소드가 어떤 매개변수를 가지고 , 반환 타입이 무엇인지에 따라 달라진다.
1) 정적 메소드 레퍼런스
이를 사용할 경우에는 클래스 이름뒤에 ::기호를 사용하여 정적 메소드 이름을 작성할 수 있다.
클래스 이름 :: 정적 메소드 이름
ex)
import java.util.function.IntBinaryOperator;
class Calculator {
public static int staticMethod(int x, int y){
return x+y;
}
}
public class Main {
public static void main(String[] args) throws Exception {
IntBinaryOperator operator;
//정적 메소드 참조
operator = Calculator::staticMethod;
System.out.println(operator.applyAsInt(5,10));
}
}
2) 인스턴스 메소드 레퍼런스
인스턴스 메소드를 참조할 경우에는 객체를 생성한 뒤 참조 변수 뒤에 ::기호를 사용하여 인스턴스 메소드 이름을 작성할 수 있다.
참조 변수 :: 인스턴스메소드 이름
ex)
class Calculator {
public in instanceMethod ( int x, int y ) {
return x + y;
}
}
public class Main{
public static void main(String[] args) throws Exception {
IntBinaryOperator operator;
// 인스턴스 메서드 참조
Calculator calculator = new Calculator();
operator = calculator::instanceMethod;
System.out.println(operator.applyAsInt(5, 10));
}
}
3) 생성자 레퍼런스
메소드 레퍼런스는 생성자 참조도 가능하다. 이는 객체 생성을 의미한다.
[람다식에서 객체를 생성하고 리턴하는 방법]
( a , b) -> { return new 클래스 이름 (a, b);};
[생성자 레퍼런스]
클래스 이름 :: new
import java.util.function.BiFunction;
import java.util.function.Function;
class Member {
private String name;
private String id;
public Member() {
System.out.println("매개변수 없는 생성자");
}
public Member(String id) {
System.out.println("id 매개 변수를 갖는 생성자");
this.id = id;
}
public Member(String name , String id){
System.out.println("두 개의 매개변수를 갖는 생성자");
this.name = name ;
this.id = id;
}
public String getName() {
return name;
}
public String getId() {
return id;
}
}
public class Main {
public static void main(String[] args) {
Function<String, Member> function1 = Member::new;
Member member1 = function1.apply("id");
BiFunction<String, String, Member> function2 = Member::new;
Member member2 = function2.apply("id", "name");
}
}
[참고 자료]
https://yejun-the-developer.tistory.com/12
람다식과 외부 변수 참조
모던 Practical 자바 5장 스트림 API를 읽다 흥미로운 코드를 발견했다. (설명을 위해 약간 변형했습니다.) List intList = Arrays.asList(1, 2, 3, 4, 5, 6, 7, 8, 9); int sum = 0; intList.stream().forEach(n -> sum+=n); System.out.
yejun-the-developer.tistory.com
[JAVA] 람다식(Lambda)의 개념 및 사용법
람다함수란? 람다 함수는 프로그래밍 언어에서 사용되는 개념으로 익명 함수(Anonymous functions)를 지칭하는 용어입니다. 현재 사용되고 있는 람다의 근간은 수학과 기초 컴퓨터과학 분야에서의 람
khj93.tistory.com
[Java/자바] 람다식(Lambda)이란? 그리고 사용법
람다식이란 ? 람다식이란 쉽게 말해 메서드를 "하나의 식"으로 표현한 것입니다. 하나의 식으로 표현하여 훨씬 간략하게 표현이 가능하게 되며, 메서드의 이름과 반환값이 없어지므로 "익명함수
hstory0208.tistory.com
https://bcp0109.tistory.com/313
Java 8 함수형 인터페이스 (Functional Interface)
Overview 함수형 인터페이스란 1 개의 추상 메소드를 갖는 인터페이스를 말합니다. Java8 부터 인터페이스는 기본 구현체를 포함한 디폴트 메서드 (default method) 를 포함할 수 있습니다. 여러 개의 디
bcp0109.tistory.com
https://ittrue.tistory.com/162
[Java] 자바 메서드 레퍼런스(Method Reference) 개념 정리 및 활용
메서드 레퍼런스란? (메서드 참조 : Method Reference) 메서드 레퍼런스는 람다식에서 불필요한 매개변수를 제거할 때 주로 사용한다. 즉, 람다식으로 더욱 간단해진 익명 객체를 보다 더 간단하게 사
ittrue.tistory.com