[ JAVA ] 함수형 인터페이스 Predicate

신범철·2023년 1월 20일
1

자바

목록 보기
16/17

서론

Udemy 강의를 듣는 도중 Predicate라는 문법의 등장으로 간단하게 정리하고 넘어가보자!

Predicate란?

predicate interface는 T에대한 조건에 대해서 true / false를 반환하는 Functional Interface입니다.
Predicat<T>로 사용되고 여기서 T는 파라미터이자 조건이다.
T가 true 또는 false를 return하도록 작성하면 된다.

함수형 인터페이스란?

  • 1개의 추상 메소드를 갖는 인터페이스
  • 디폴트 메소드는 많이 존재할 수 있다.
  • 자바의 람다 표현식은 함수형 인터페이스로만 사용 가능하다.
  • 함수형 인터페이스 예제
@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");
    }
}

@FunctionalInterface로 함수형 인터페이스를 명시하고 형식에 맞춰 만들면됨

Java에서 제공하는 함수형 인터페이스

대부분 제공하는 함수형 인터페이스로 람다식 구현 가능

Predicate 구성

@FunctionalInterface
public interface Predicate<T> {
    // 주어진 arguments를 검증
    boolean test(T t);

    // 다른 Predicate와 연결하는 역할 &&
    default Predicate<T> and(Predicate<? super T> other) {
        Objects.requireNonNull(other);
        return (t) -> test(t) && other.test(t);
    }

    // test()의 반대 결과 반환 (ex: true -> false)
    default Predicate<T> negate() {
        return (t) -> !test(t);
    }

    // 다른 Predicate와 연결하는 역할 ||
    default Predicate<T> or(Predicate<? super T> other) {
        Objects.requireNonNull(other);
        return (t) -> test(t) || other.test(t);
    }

    // 동일한지 체크
    static <T> Predicate<T> isEqual(Object targetRef) {
        return (null == targetRef)
                ? Objects::isNull
                : object -> targetRef.equals(object);
    }

    @SuppressWarnings("unchecked")
    static <T> Predicate<T> not(Predicate<? super T> target) {
        Objects.requireNonNull(target);
        return (Predicate<T>)target.negate();
    }
}

Predicate의 대표적인 사용 예제

바로 Stream의 filter에서 사용한다.
stream에서 filter는 stream의 요소중 통과할 요소와 제거할 요소를 걸러내는 작업을 해주는 함수형 명령어 이다.

예시

    public void deleteById(int id) {
        //predicate에는 조건이 들어감
        Predicate<? super Todo> predicate = todo -> todo.getId() == id;
        todos.removeIf(predicate);
    }

    public Todo findById(int id) {
        //predicate에는 조건이 들어감
        Predicate<? super Todo> predicate = todo -> todo.getId() == id;
        return todos.stream().filter(predicate).findFirst().get();
    }
    
    @Test
public void predicateTest() {
    Predicate<Integer> justOne = integer -> integer == 1;

        Stream<Integer> integerStream = Stream.of(1, 2);
        Stream<Integer> filteredStream = integerStream.filter(justOne);
        System.out.println("collect = " + filteredStream.collect(toList()));
}

결론

자바에서 람다 표현식은 함수형 인터페이스로만 사용 가능하다.
함수형 인터페이스를 통해 코드 단축과 가독성을 극대화해보자 :)

참고 문헌

함수형 인터페이스 설명

predicate 예제

predcate 정의

profile
https://github.com/beombu

0개의 댓글