• 함수형 인터페이스
    Language/Java 2023. 12. 1. 00:01

    Functional Interface

    java 8에서 도입된 개념으로 정확히 하나의 추상 메서드를 가진 인터페이스를 말한다.

    이 함수형 인터페이스는 람다 표현식으로 잘 활용된다.


    자바에는 여러가지 내장된 함수형 인터페이스가 있지만,

    특히 자바 공부할 때

    기능 설명 부분에서 자주 볼 수 있었던

    몇 가지 인터페이스에 대해서 정리 ✏️



    Function<T, R>

    매개변수     : T Return 타입 : R 추상 메서드 : apply()           기능 : T 타입의 인자를 받으며, R 타입의 결과를 반환한다.

    사용 예시

    기본 표현 방식 사용

    public static void getLastIndex(String text) {
    Function<String, Integer> getBasicLastIndex = new Function<String, Integer>() {
    @Override
    public Integer apply(String s) {
    return s.length() - 1;
    }
    };
    System.out.println(
    getBasicLastIndex.apply(text)
    );
    }

    람다 표현 방식 사용

    public static void getLastIndex(String text) {
    Function<String, Integer> getLambdaLastIndex = s -> s.length() - 1;
    System.out.println(
    getLambdaLastIndex.apply(text)
    );
    }

    Function 에서 사용할 수 있는 Default 메서드

    🤓✏️ Default 메서드

    자바 8에서 추가된 기능으로
    인터페이스에서 선언과 구현을 동시에 하는 방법이다.
    인터페이스를 정의할 때 default 키워드를 사용하여 메서드를 작성하면 된다.
    디폴트 메서드를 사용하면,
    인터페이스에 새로운 메서드(default)를 추가하더라도
    기존에 사용중이던 클래스를 수정하지 않고도 인터페이스에 추가된 메서드를 사용할 수 있다.
    주의 할 부분은
    여러 인터페이스에서 동일한 디폴트 메서드를 제공하는 경우
    충돌이 발생할 수 있으므로 유의해서 사용해야 한다.

    * andThen()

    주어진 함수를 첫 번째 함수의 결과에 적용하여 새로운 자료형의 반환값을 반환한다.

    f.andThen(g) 형태로 사용하며, 수학적으로 표현하면 g(f(x))와 같다.

    Function<Integer, Integer> f1 = num -> num * 2;
    Function<Integer, Integer> f2 = num -> num * num;
    Function<Integer, Integer> f = f1.andThen(f2);
    System.out.println(f.apply(3));

    위에 작성한 코드를 보면 마지막 sout 문장 안에 있는 andThen 결과인 f에 3을 주었다.

    3f1에서 f1의 구현 내용으로 가공된 후 , 반환값이f2에 들어가서 f2의 구현 내용에 따라 2차 가공되어 최종 반환된다.

    이 경우 3 -> 3*2 -> 6*6 -> 36 순서로 값의 변화가 일어난다.

    * compose()

    compose()는 반대로 첫 번째 함수의 결과를 두 번째 함수에 적용한다.

    f.andThen(g) 형태로 사용하며, 수학적으로 표현하면 f(g(x))와 같다.



    아래 부터 소개하는 인터페이스의 디폴트 메서드는 나중에 정리 😵‍💫

    Predicate<T>

    매개변수     : T Return 타입 : boolean 추상 메서드 : test()           기능 : T 타입의 인자를 받으며 boolean을 반환한다.

    사용 예시

    기본 표현 방식 사용

    public static void isEvenOdd() {
    Predicate<Integer> predicate = new Predicate<Integer>() {
    @Override
    public boolean test(Integer integer) {
    return integer % 2 == 0;
    }
    };
    System.out.println(
    predicate.test(2)
    ? "짝수 입니다."
    : "홀수 입니다."
    );
    }

    람다 표현 방식 사용

    public static void isEvenOdd() {
    Predicate<Integer> predicate2 = i -> i % 2 == 0;
    System.out.println(
    predicate2.test(3)
    ? "짝수 입니다."
    : "홀수 입니다."
    );
    }



    Consumer<T>

    매개변수     : T Return 타입 : void 추상 메서드 : accept()           기능 : T 타입의 인자를 받으며, 아무런 결과도 반환하지 않는다.

    결과를 반환하지 않고 값을 사용하기만 해서 소비자인가 🙊

    사용 예시

    기본 표현 방식 사용

    public static void print() {
    Consumer<String> consumer = new Consumer<String>() {
    @Override
    public void accept(String s) {
    System.out.printf("\"%s\" 입력 받았슴다 🤓\n", s);
    }
    };
    consumer.accept("가나다라");
    }

    람다 표현 방식 사용

    public static void print() {
    Consumer<String> consumer2 = s -> System.out.printf("\"%s\" 입력 받았슴다 🤓\n", s);
    consumer2.accept("아자차카타파하하하하하");
    }

    메서드 참조 표현식 사용

    메서드 참조 🤓✏️ > 지금은 간단히 적어두고 나중에 추가 공부 계획

    자바 8에서 도입

    이미 정의된 메서드를 람다 표현식 대신에 직접 참조할 수 있게 해준다.

    4가지 유형의 사용 방법이 있음!

    1. 정적(static) 메서드 참조 : 클래스::정적메서드 ex : Integer::parseInt

    2. 인스턴스 메서드 참조 : 인스턴스::메서드 ex : System.out::println

    3. 비한정적 인스턴스 메서드 참조 : 클래스::메서드 ex : String::length

    4. 생성자 참조 : 클래스::new ex : ArrayList::new

    public static void print() {
    Consumer<String> consumer3 = System.out::println;
    consumer3.accept("하하 🙈");
    }

    이렇게 사용하면 Consumer.accept(T t) = System.out.println(t) 이런식으로 적용 된다.



    Supplier<T>

    매개변수     : void Return 타입 : T 추상 메서드 : get()           기능 : 인자를 받지 않고, T 타입의 결과를 반환한다.

    오, Getter()랑 같은 기능! 그러면 반대로 동작하는 Consumer.accept() 는 Setter() !! 🙊

    공급자는 get() == getter() 소비자는 accept() == setter() 🙊

    주로 특정 값을 생성하거나, 계산하는데 사용된다고 한다.

    사용 예시

    기본 표현 방식 사용

    public static void getNowTime() {
    Supplier<LocalDateTime> supplier = new Supplier<LocalDateTime>() {
    @Override
    public LocalDateTime get() {
    return LocalDateTime.now();
    }
    };
    System.out.println(
    supplier.get()
    );
    }

    람다 표현식 사용

    public static void getNowTime() {
    Supplier<LocalDateTime> supplier2 = () -> LocalDateTime.now();
    System.out.println(
    supplier2.get()
    );
    }

    메서드 참조 방식 사용

    public static void getNowTime() {
    Supplier<LocalDateTime> supplier3 = LocalDateTime::now;
    System.out.println(
    supplier3.get()
    );
    }



    UnaryOperator<T>

    매개변수     : T Return 타입 : T 추상 메서드 : T apply(T t)           기능 : 인자로 T를 받고, T를 반환한다.

    Function<T, T> 를 확장한 인터페이스 이다. Function의 apply() 메서드를 그대로 사용한다. Function과 UnaryOperator의 차이점으로는 Function은 매개변수와 결과값의 자료형이 달라질 수 있고 UnaryOperator는 매개변수와 결과값의 자료형이 같아야 한다.

    사용 예시

    기본 표현 방식 사용

    public static void getPow() {
    UnaryOperator<Integer> uo = new UnaryOperator<Integer>() {
    @Override
    public Integer apply(Integer num) {
    return num * num;
    }
    };
    System.out.println( uo.get() );
    }

    람다 표현 방식 사용

    public static void getPow() {
    UnaryOperator<Integer> uo = num -> num * num;
    System.out.println( uo.get() );
    }



    BinaryOperator<T>

    매개변수     : T Return 타입 : T 추상 메서드 : T apply(T t, T t)           기능 : T 타입의 인자를 2개 받고, T를 반환한다.

    사용 예시

    기본 표현 방식 사용

    public static void print(String str1, String str2) {
    BinaryOperator<String> bo = new BinaryOperator<String>() {
    @Override
    public String apply(String s, String s2) {
    return s.length() >= s2.length() ? s : s2;
    }
    };
    System.out.println( bo.apply("monkey", "monday..") );
    }

    람다 표현 방식 사용

    public static void print2(String str1, String str2) {
    BinaryOperator<String> bo = (s, s2) -> s.length() >= s2.length() ? s : s2;
    System.out.println( bo.apply("monkey", "monday..") );
    }





    앞으로 강의 실습 계속 하면서 새롭고 낯선 함수형 인터페이스를 만나게 되면 추가할 계획!

    'Language > Java' 카테고리의 다른 글

    UUID.randomUUID()  (0) 2023.12.01
    Stream  (0) 2023.12.01
    enum 클래스  (0) 2023.11.30
    Optional  (0) 2023.11.30
    자바 메모리 모델 Java Memory Model  (0) 2023.11.30

Designed by Tistory / Custom by 얼거스