Post

Lambda, Functional Interface ๋ฌด์Šจ ๊ด€๊ณ„


๋žŒ๋‹ค ํ‘œํ˜„์‹์€ ์ž๋ฐ”์˜ ๋ฉ”์„œ๋“œ๋ฅผ ํ•˜๋‚˜์˜ ์‹์œผ๋กœ ๊ฐ„๊ฒฐํ•˜๊ฒŒ ํ‘œํ˜„ํ•œ ๊ฒƒ์ด๋‹ค.
์ด์ „์—๋Š” ์ž๋ฐ”์—์„œ ๋ฉ”์„œ๋“œ๋ฅผ ํ‘œํ˜„ํ•˜๋ ค๋ฉด ํด๋ž˜์Šค๋ฅผ ์ •์˜ํ•ด์•ผ ํ–ˆ์ง€๋งŒ, ์ž๋ฐ” 8 ๋ถ€ํ„ฐ ๋žŒ๋‹ค์‹์„ ์ด์šฉํ•ด ๋ฉ”์„œ๋“œ์˜ ์ด๋ฆ„๊ณผ ๋ฐ˜ํ™˜ ๊ฐ’์„ ์ƒ๋žตํ•  ์ˆ˜ ์žˆ๊ณ , ์ด๋ฅผ ๋ณ€์ˆ˜์— ๋„ฃ์–ด ์ฝ”๋“œ๋ฅผ ๊ฐ„๊ฒฐํ•˜๊ฒŒ ํ•œ๋‹ค.

1
2
3
4
5
6
int add (int a, int b) {
    return a + b; 
}

// ์•„๋ž˜์™€ ๊ฐ™์ด ๋ณ€๊ฒฝํ•  ์ˆ˜ ์žˆ๋‹ค.
(a, b) -> a + b;


(๋งค๊ฐœ๋ณ€์ˆ˜) -> {ํ•จ์ˆ˜ ๋ณธ๋ฌธ} ์˜ ํ˜•ํƒœ๋กœ,

๋งค๊ฐœ ๋ณ€์ˆ˜๊ฐ€ ์—†๋Š” ๊ฒฝ์šฐ () ๋ฅผ ์‚ฌ์šฉํ•˜๊ณ , ๋งค๊ฐœ ๋ณ€์ˆ˜๊ฐ€ ํ•˜๋‚˜ ์ธ ๊ฒฝ์šฐ ๊ด„ํ˜ธ๋ฅผ ์ƒ๋žตํ•  ์ˆ˜ ์žˆ์œผ๋ฉฐ, ํ•จ์ˆ˜์˜ ๋ณธ๋ฌธ์ด ํ•˜๋‚˜์ธ ๊ฒฝ์šฐ ์ค‘๊ด„ํ˜ธ์™€ return์„ ์ƒ๋žตํ•  ์ˆ˜ ์žˆ๋‹ค.

1
2
3
4
5
6
7
8
9
10
11
// ๋งค๊ฐœ๋ณ€์ˆ˜๊ฐ€ ์—†๊ณ , ํ‘œํ˜„์‹์ด ํ•˜๋‚˜
() -> System.out.println("hello"):

// ๋งค๊ฐœ ๋ณ€์ˆ˜๊ฐ€ ํ•˜๋‚˜
x -> x * x;

// ๋งค๊ฐœ๋ณ€์ˆ˜๊ฐ€ ์—ฌ๋Ÿฌ ๊ฐœ์ด๊ณ , ๋ณธ๋ฌธ์ด ์—ฌ๋Ÿฌ ์ค„
(x, y) -> {
    int sum = x + y;
    return sum;
}



๋žŒ๋‹ค์‹์€ ์ž๋ฐ”์—์„œ ํ•จ์ˆ˜ํ˜• ํ”„๋กœ๊ทธ๋ž˜๋ฐ์„ ํ•  ์ˆ˜ ์žˆ๋„๋ก ๋„์™€์ค€๋‹ค. ์ž๋ฐ”์—์„œ ์ธํ„ฐํŽ˜์ด์Šค๋Š” ๋ฉ”์„œ๋“œ๋ฅผ ์ •์˜๋งŒํ•˜๊ณ  ๊ตฌํ˜„์€ ํ•˜์ง€ ์•Š๋Š”๋‹ค. ๊ทธ๋ž˜์„œ ์ธํ„ฐํŽ˜์ด์Šค๋ฅผ ์‚ฌ์šฉํ•˜๊ธฐ ์œ„ํ•ด์„œ๋Š” ํด๋ž˜์Šค๋ฅผ ์ž‘์„ฑํ•˜๊ณ  ๋ฉ”์„œ๋“œ๋ฅผ ์˜ค๋ฒ„๋ผ์ด๋“œํ•˜๋Š” ์ž‘์—…์„ ํ•ด์ฃผ์—ˆ๋‹ค. ์˜ˆ๋กœ A ์ธํ„ฐํŽ˜์ด์Šค์— void run()์ด๋ผ๋Š” ๋ฉ”์„œ๋“œ๊ฐ€ ์žˆ์œผ๋ฉด, ์ด ๋ฉ”์„œ๋“œ๋ฅผ ์‹ค์ œ๋กœ ๋™์ž‘ํ•˜๊ฒŒ ํ•  ๋ฐฉ๋ฒ•์ด ํ•„์š”ํ•˜๋‹ค.

๋žŒ๋‹ค๋Š” ์ด ์ธํ„ฐํŽ˜์ด์Šค์˜ ๋ฉ”์„œ๋“œ๋ฅผ ๊ตฌํ˜„ํ•˜๊ธฐ ์œ„ํ•ด์„œ ์‚ฌ์šฉ๋œ๋‹ค. Runnable ์ธํ„ฐํŽ˜์ด์Šค๊ฐ€ ์žˆ์„ ๋•Œ, run()๋ฉ”์„œ๋“œ๋Š” ๊ตฌํ˜„๋˜์ง€ ์•Š์•˜๋‹ค.
๊ทธ๋ž˜์„œ ์šฐ๋ฆฌ๊ฐ€ ๋žŒ๋‹ค๋ฅผ ์‚ฌ์šฉํ•ด์„œ run()๋ฉ”์„œ๋“œ๋ฅผ ๊ตฌํ˜„ํ•  ์ˆ˜ ์žˆ๋‹ค.

Runnable.java

1
2
3
4
5
@FunctionalInterface
public interface Runnable {

    public abstract void run();
}
1
2
Runnable runnable = () -> System.out.println("Hello, World!");
runnable.run();



๊ทธ๋Ÿฌ๋ฉด ๋žŒ๋‹ค์‹์€ ์–ด๋–ค ํŠน์ง•์„ ๊ฐ€์งˆ๊นŒ?

1. ์šฐ์„ , ๋žŒ๋‹ค์‹์„ ์‚ฌ์šฉํ•˜๋ฉด ์ฝ”๋“œ๊ฐ€ ๊ฐ„๊ฒฐํ•˜๋‹ค.

1
2
3
4
5
6
7
8
9
10
// ์ต๋ช… ํด๋ž˜์Šค๋กœ Runnable ๊ตฌํ˜„
Runnable r1 = new Runnable() {
    @Override
    public void run() {
        System.out.println("Hello, World!");
    }
};

// ๋žŒ๋‹ค ํ‘œํ˜„์‹์œผ๋กœ Runnable ๊ตฌํ˜„
Runnable r2 = () -> System.out.println("Hello, World!");


3. ์ปฌ๋ ‰์…˜ ์ž‘์—…์ด ๊ฐ„ํŽธํ•˜๋‹ค.

Java 8์—์„œ๋Š” Stream API์™€ ํ•จ๊ป˜ ๋žŒ๋‹ค ํ‘œํ˜„์‹์„ ๋„์ž…ํ•˜์—ฌ, ๋ฐ์ดํ„ฐ ์ฒ˜๋ฆฌ์™€ ๋ณ€ํ™˜์„ ๊ฐ„ํŽธํ•˜๊ฒŒ ํ•  ์ˆ˜ ์žˆ๋‹ค.

1
2
3
4
5
6
7
8
9
10
11
12
13
import java.util.Arrays;
import java.util.List;

public class LambdaExample {
    public static void main(String[] args) {
        List<Integer> list = Arrays.asList(1, 2, 3, 4, 5, 6, 7, 8, 9);

        // ๋ณ‘๋ ฌ ์ฒ˜๋ฆฌ
        list.parallelStream()
            .filter(n -> n % 2 == 0)
            .forEach(System.out::println);
    }
}


2. ํ•จ์ˆ˜ํ˜• ํ”„๋กœ๊ทธ๋ž˜๋ฐ์„ ์ง€์›ํ•œ๋‹ค.

์ž๋ฐ”๋Š” ๊ฐ์ฒด ์ง€ํ–ฅ ์–ธ์–ด์ง€๋งŒ, ๋žŒ๋‹ค๋ฅผ ํ†ตํ•ด ์ผ๊ธ‰ ๊ฐ์ฒด๋กœ ํ•จ์ˆ˜๋ฅผ ๋‹ค๋ฃฐ ์ˆ˜ ์žˆ๋‹ค.

์ต๋ช… ํ•จ์ˆ˜๋ž€?

์ด๋ฆ„์ด ์—†๋Š” ํ•จ์ˆ˜๋กœ, ์ต๋ช… ํ•จ์ˆ˜๋Š” ๋ชจ๋‘ ์ผ๊ธ‰ ๊ฐ์ฒด์ด๋‹ค. ์ผ๊ธ‰ ๊ฐ์ฒด์ธ ํ•จ์ˆ˜๋Š” ๋ณ€์ˆ˜์ฒ˜๋Ÿผ ์‚ฌ์šฉ์ด ๊ฐ€๋Šฅํ•˜๋ฉฐ, ๋งค๊ฐœ๋ณ€์ˆ˜๋กœ ์ „๋‹ฌ์ด ๊ฐ€๋Šฅํ•˜๋‹ค.

1
2
3
4
5
6
7
8
9
import java.util.function.Function;

public class LambdaExample {
    public static void main(String[] args) {
        Function<Integer, Function<Integer, Integer>> add = x -> y -> x + y;

        System.out.println(add.apply(2).apply(3));  // ์ถœ๋ ฅ: 5
    }
}


๋žŒ๋‹ค๋Š” ํ•จ์ˆ˜ํ˜• ์ธํ„ฐํŽ˜์ด์Šค๋ฅผ ์ง€์›ํ•œ๋‹ค๊ณ  ํ•œ๋‹ค. ๊ทธ๋Ÿฌ๋ฉด ํ•จ์ˆ˜ํ˜• ์ธํ„ฐํŽ˜์ด์Šค๊ฐ€ ๋ญ˜๊นŒ?
ํ•จ์ˆ˜ํ˜• ์ธํ„ฐํŽ˜์ด์Šค๋Š” ๋‹จ ํ•˜๋‚˜์˜ ์ถ”์ƒ ๋ฉ”์„œ๋“œ๋ฅผ ๊ฐ–๋Š” ์ธํ„ฐํŽ˜์ด์Šค์ด๋‹ค. ์ถ”์ƒ ๋ฉ”์„œ๋“œ๋งŒ ๋‹จ ํ•˜๋‚˜๋ฅผ ๊ฐ–๋Š”๋‹ค.!!! ๊ทธ ์™ธ ๋ฉ”์„œ๋“œ๋Š” ์ƒ๊ด€์ด ์—†๋‹ค. ๋žŒ๋‹ค์‹์€ ์ด ์ธํ„ฐํŽ˜์ด์Šค์˜ ์ธ์Šคํ„ด์Šค๋ฅผ ์ƒ์„ฑํ•˜๋Š”๋ฐ ์‚ฌ์šฉ๋œ๋‹ค.


Java8์—์„œ ์ œ๊ณตํ•˜๋Š” ์ฃผ์š” ํ•จ์ˆ˜ํ˜• ์ธํ„ฐํŽ˜์ด์Šค๋ฅผ ์‚ดํŽด๋ณด์ž.. ์–ด๋–ป๊ฒŒ ์‚ฌ์šฉ๋˜๋Š”์ง€๋„ ๊ฐ™์ด ๋ณด์ž.


Runnable

์Šค๋ ˆ๋“œ๋ฅผ ์‹คํ–‰ํ•˜๊ธฐ ์œ„ํ•œ ํ•จ์ˆ˜ํ˜• ์ธํ„ฐํŽ˜์ด์Šค แ„‰แ…ณแ„แ…ณแ„…แ…ตแ†ซแ„‰แ…ฃแ†บ 2024-11-07 แ„‹แ…ฉแ„’แ…ฎ 2 56 15

run()์ถ”์ƒ ๋ฉ”์„œ๋“œ๋ฅผ ๊ฐ–๊ณ , ๋งค๊ฐœ๋ณ€์ˆ˜๋ฅผ ๋ฐ›์ง€ ์•Š์œผ๋ฉฐ ๋ฐ˜ํ™˜๊ฐ’์ด ์—†๋‹ค.

แ„‰แ…ณแ„แ…ณแ„…แ…ตแ†ซแ„‰แ…ฃแ†บ 2024-11-07 แ„‹แ…ฉแ„’แ…ฎ 2 54 23

Thread ํด๋ž˜์Šค์˜ ์ƒ์„ฑ์ž ์ค‘ ํ•˜๋‚˜๋กœ Runnable ๊ฐ์ฒด๋ฅผ ๋งค๊ฐœ๋ณ€์ˆ˜๋กœ ๋ฐ›์•„ ์Šค๋ ˆ๋“œ์˜ ์‹คํ–‰ ์ž‘์—…์„ ์ •์˜ํ•˜๋Š”๋ฐ ์‚ฌ์šฉ๋œ๋‹ค.

์•„๋ž˜์™€ ๊ฐ™์ด ๊ตฌํ˜„ํ•  ์ˆ˜ ์žˆ๋‹ค.

1
2
3
4
5
6
7
8
9
10
public class RunnableExample {
    public static void main(String[] args) {
        // Runnable ์ธํ„ฐํŽ˜์ด์Šค๋ฅผ ๋žŒ๋‹ค์‹์œผ๋กœ ๊ตฌํ˜„
        Runnable task = () -> System.out.println("Task is running in a thread");

        // Runnable์„ ์Šค๋ ˆ๋“œ์— ์ „๋‹ฌํ•˜๊ณ  ์‹คํ–‰
        Thread thread = new Thread(task);
        thread.start();
    }
}


Function<T, R>

T ํƒ€์ž…์˜ ๋งค๊ฐœ๋ณ€์ˆ˜๋ฅผ ์ž…๋ ฅ ๋ฐ›์•„, R์„ ๋ฆฌํ„ดํ•œ๋‹ค.

  • R apply (T t)
    1
    2
    3
    4
    
    @FunctionalInterface
    public interface Function<T, R> {
      R apply(T t);
    }
    

แ„‰แ…ณแ„แ…ณแ„…แ…ตแ†ซแ„‰แ…ฃแ†บ 2024-11-07 แ„‹แ…ฉแ„’แ…ฎ 3 14 17

map ๋ฉ”์„œ๋“œ์˜ ๋งค๊ฐœ๋ณ€์ˆ˜๋กœ ์ „๋‹ฌ๋œ๋‹ค. ์ŠคํŠธ๋ฆผ์˜ ๊ฐ ์š”์†Œ๋ฅผ Function์„ ์‚ฌ์šฉํ•ด ๋ณ€ํ™˜ํ•œ ํ›„ ์ƒˆ๋กœ์šด ์ŠคํŠธ๋ฆผ์„ ๋ฐ˜ํ™˜ํ•œ๋‹ค.

  • Function<? super T, ? extends R> mapper๋Š” ๋ณ€ํ™˜์„ ์ˆ˜ํ–‰ํ•˜๋Š” ํ•จ์ˆ˜๋กœ, ์ŠคํŠธ๋ฆผ์˜ ๊ฐ ์š”์†Œ(T)๋ฅผ ๋ฐ›์•„ ์ƒˆ๋กœ์šด ๊ฐ’(R)์„ ์ƒ์„ฑํ•œ๋‹ค.
1
2
3
4
5
6
7
8
9
10
11
public class MapExample {

    public static void main(String[] args) {

        List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5);

        List<Integer> squares = numbers.stream()
            .map(n -> n * n)
            .collect(Collectors.toList());
    }
}

์—ฌ๊ธฐ์„œ map(n -> n * n) ์—์„œ n์˜ ํƒ€์ž…์ด ๋ช…์‹œ๋˜์ง€ ์•Š์•˜์ง€๋งŒ, ์ปดํŒŒ์ผ๋Ÿฌ๋Š” numbers ๋ฆฌ์ŠคํŠธ๊ฐ€ Integer ์ธ ๊ฒƒ์„ ์•Œ๊ณ  ์žˆ๊ธฐ ๋•Œ๋ฌธ์— n๋„ Integer๋ผ๊ณ  ์ถ”๋ก ํ•œ๋‹ค. ์ด๊ฑธ ํƒ€์ž… ์ถ”๋ก ์ด๋ผ๊ณ  ํ•œ๋‹ค.
์ž…๋ ฅ์„ ๋ฐ›์•„์„œ ์ถœ๋ ฅ์œผ๋กœ ๋ณ€ํ™˜ํ•˜๋ฉฐ, ์ฃผ๋กœ ๋ณ€ํ™˜ ์ž‘์—…์— ์‚ฌ์šฉ๋œ๋‹ค.


Predicate< T >

Tํƒ€์ž…์˜ ๋งค๊ฐœ๋ณ€์ˆ˜๋ฅผ ์ž…๋ ฅ ๋ฐ›์•„, ์กฐ๊ฑด ๊ฒ€์‚ฌ ํ›„ boolean ๊ฐ’์„ ๋ฐ˜ํ™˜ํ•œ๋‹ค.

  • boolean test(T t)

แ„‰แ…ณแ„แ…ณแ„…แ…ตแ†ซแ„‰แ…ฃแ†บ 2024-11-07 แ„‹แ…ฉแ„’แ…ฎ 4 20 06

แ„‰แ…ณแ„แ…ณแ„…แ…ตแ†ซแ„‰แ…ฃแ†บ 2024-11-07 แ„‹แ…ฉแ„’แ…ฎ 3 28 39

์ž…๋ ฅ ๊ฐ’์— ๋Œ€ํ•ด boolean ๊ฐ’์„ ๋ฐ˜ํ™˜ํ•˜๋ฉฐ, ์ฃผ๋กœ ์กฐ๊ฑด ๊ฒ€์ฆ์— ์‚ฌ์šฉํ•œ๋‹ค.


Consumer< T >

Tํƒ€์ž…์˜ ์ž…๋ ฅ์„ ๋ฐ›์•„ ๋™์ž‘์„ ์ˆ˜ํ–‰ํ•œ ํ›„, ๊ฒฐ๊ณผ๋ฅผ ๋ฐ˜ํ™˜ํ•˜์ง€ ์•Š๋Š”๋‹ค.

  • void accept(T t)

แ„‰แ…ณแ„แ…ณแ„…แ…ตแ†ซแ„‰แ…ฃแ†บ 2024-11-07 แ„‹แ…ฉแ„’แ…ฎ 4 23 06

แ„‰แ…ณแ„แ…ณแ„…แ…ตแ†ซแ„‰แ…ฃแ†บ 2024-11-07 แ„‹แ…ฉแ„’แ…ฎ 4 14 31

์ž…๋ ฅ์„ ๋ฐ›์•„์„œ ๋™์ž‘์„ ์ˆ˜ํ–‰ํ•˜๋ฉฐ, ๊ฒฐ๊ณผ๋ฅผ ๋ฐ˜ํ™˜ํ•˜์ง€ ์•Š๋Š”๋‹ค.


Supplier< T >

๋งค๊ฐœ๋ณ€์ˆ˜ ์—†์ด Tํƒ€์ž…์˜ ๊ฐ’์„ ๋ฐ˜ํ™˜ํ•˜๋Š” ํ•จ์ˆ˜ํ˜• ์ธํ„ฐํŽ˜์ด์Šค๋กœ ๊ฐ์ฒด๋ฅผ ์ƒ์„ฑํ•˜๊ฑฐ๋‚˜ ๊ฐ’์„ ์ œ๊ณตํ•œ๋‹ค.

  • T get()

แ„‰แ…ณแ„แ…ณแ„…แ…ตแ†ซแ„‰แ…ฃแ†บ 2024-11-07 แ„‹แ…ฉแ„’แ…ฎ 4 23 16

แ„‰แ…ณแ„แ…ณแ„…แ…ตแ†ซแ„‰แ…ฃแ†บ 2024-11-07 แ„‹แ…ฉแ„’แ…ฎ 4 17 22

๋งค๊ฐœ ๋ณ€์ˆ˜๋ฅผ ๋ฐ›์ง€ ์•Š๊ณ , ๊ฐ’์„ ์ƒ์„ฑํ•˜๊ฑฐ๋‚˜ ์ œ๊ณตํ•œ๋‹ค.

This post is licensed under CC BY 4.0 by the author.