study

function 패키지 사용법, 기본

기본 핵심 인터페이스

  1. Function<T, R>, Consumer<T>, Supplier<R>, Predicate<T>
    • Function<T, R>: T 타입 입력 받아 R 타입 리턴, 입력 → 출력, R = apply(T)
    • Consumer<T>: T 타입 입력 받아 소비(리턴 없음), 입력만(사이드 이펙트), accept(T) 실행
    • Supplier<R>: 아무 입력도 없고 R 타입 리턴, 출력만(공급), R = get()
    • Predicate<T>: T 타입 입력 받아 boolean 반환, 조건/검사, boolean = test(T) 실행
import java.util.function.Consumer;
import java.util.function.Function;
import java.util.function.Predicate;
import java.util.function.Supplier;

public class FunctionTest {

    public static void main(String... strings) {
        
        // Function<T, R>: T 타입 입력 받아 R 타입 리턴
        Function<String, Integer> stringLength = str -> str.length();
        System.out.println(stringLength.apply("Hello")); // 5

        // Consumer<T>: T 타입 입력 받아 소비(리턴 없음)
        Consumer<String> printer = str -> System.out.println(str);
        printer.accept("Hello World");

        // Supplier<T>: 아무 입력도 없고 T 타입 리턴
        Supplier<Long> timeSupplier = () -> System.currentTimeMillis();
        System.out.println(timeSupplier.get());

        // Predicate<T>: T 타입 입력 받아 boolean 반환
        Predicate<String> isEmpty = str -> str.isEmpty();
        System.out.println(isEmpty.test(""));   // true
        System.out.println(isEmpty.test("hi")); // false
    }    
}
  1. 조합 (andThen, compose, etc.)
    • andThen: multiply2 실행 후 square 실행, f.andThen(g) ≡ g(f(x))
    • compose: square 실행 후 multiply2 실행, f.compose(g) ≡ f(g(x))
public class FunctionTest3 {

    public static void main(String... strings) {

        // 조합 (andThen, compose, etc.)
        Function<Integer, Integer> multiply2 = x -> x * 2;
        Function<Integer, Integer> square = x -> x * x;

        Function<Integer, Integer> andThenTest = multiply2.andThen(square);
        System.out.println(andThenTest.apply(3)); // 3*2 = 6 -> 6 * 6 = 36 
        
        Function<Integer, Integer> composeTest = multiply2.compose(square);
        System.out.println(composeTest.apply(3)); // 3*3 = 9 -> 9 * 2 = 18
    }    
}
  1. 스트림
    • filterPredicate<T>
    • mapFunction<T,R>
    • forEachConsumer<T>
import java.util.List;

public class FunctionTest4 {

    public static void main(String... strings) {
        // 스트림 map, filter, forEach
        List<String> names = List.of("Alice", "Bob", "Charlie");

        // filter (Predicate), map (Function), forEach (Consumer)
        names.stream()
            .filter(name -> name.length() > 3)  // Predicate
            .map(String::toUpperCase)           // Function
            .forEach(System.out::println);      // Consumer
    }    
}
  1. 콜백 형태
    • 개인적으로 궁금해서, 찾아보았습니다.
public class FunctionTest5 {

    public static void funcCallback(String input, Function<String, String> callback) {
        String result = callback.apply(input);
        System.out.println("처리 결과: " + result);
    }

    public static void main(String... strings) {
        funcCallback("hello", str -> str.toUpperCase());  // 콜백 전달
        funcCallback("hello", str -> "[" + str + "]");    // 다른 콜백
    }    
}

기본형 특화 인터페이스

import java.util.function.IntFunction;
import java.util.function.IntPredicate;
import java.util.function.IntSupplier;

public class FunctionTest2 {
    
    public static void main(String... strings) {

        // IntFunction<R>, IntConsumer, IntPredicate, IntSupplier        
        IntFunction intFunction = num -> num;
        System.out.println(intFunction.apply(5)); // 5

        java.util.function.IntConsumer IntConsumer = num -> System.out.println(num);
        IntConsumer.accept(2); // 2

        IntSupplier intSupplier = () -> 0;
        System.out.println(intSupplier.getAsInt());
        
        IntPredicate isEven = num -> num % 2 == 0;
        System.out.println(isEven.test(4)); // true
    }    
}