개발자는 기록이 답이다

패스트캠퍼스 환급챌린지 1일차 미션 (2월 1일) : Spring Webflux 완전 정복 : 코루틴부터 리액티브 MSA 프로젝트까지 강의 후기 본문

패스트캠퍼스

패스트캠퍼스 환급챌린지 1일차 미션 (2월 1일) : Spring Webflux 완전 정복 : 코루틴부터 리액티브 MSA 프로젝트까지 강의 후기

slow-walker 2024. 2. 1. 23:51

 

함수형 인터페이스

 

  • 함수형 프로그래밍을 지원하기 위해 java8부터 도입
  • 1개의 추상 메서드를 갖고 있는 인터페이스
  • 함수를 1급 객체로 사용할 수 있다
  • 함수를 변수에 할당하거나 인자로 전달하고 반환값으로 사용 가능
  • Funtion, Consumer, Supplier, Runnable 등
@FunctionalInterface
public interface Function<T,R> {
    R apply(T t);
}


@FunctionalInterface
public interface Consumer<T> {
    void accpet(T t);
}


@FunctionalInterface
public interface Supplier<T> {
    T get();
}


@FunctionalInterface
public interface Runnable {
    public abstract  void run();
}

 

  • 함수형 인터페이스를 구현한 익명 클래스를 람다식으로 변경 가능
  • 함수형 인터페이스는 호출한 쓰레드에서 실행된다

 

 

동기(Synchronous)

 

@Slf4j
public class Synchronous {
    public static void main(String[] args) {
        log.info("Start main");
        var result = getResult();
        var nextValue = 1;
        assert nextValue == 1;
        log.info("Finish main");
    }
    public static int getResult() {
        log.info("Start getResult");
        try {
            Thread.sleep(1000);
        } catch (InterruptedException e) {
            throw new RuntimeException();
        }
        
        var result = 0;
        try {
            return  result;
        } finally {
            log.info("Finish getResult");
        }
    }
}

 

  • caller는 callee의 결과에 관심이 있다.
    • main메소드는 gerResult메소드의 결과에 관심이 있다.
  • caller는 결과를 이용해서 action을 수행한다.
    • main메소드는 결과를 이용해서 다음 코드를 실행한다.
  • caller와 callee가 동기화되어있다.

 

 

비동기(Asynchronous)

 

@Slf4j
public class Asynchronous {
    public static void main(String[] args) {
        log.info("Start main");
        getResult(new Consumer<Integer>() {
            @Override
            public void accpet(Integer integer) {
                var nextValue = integer + 1;
                assert nextValue == 1;
            }
        });
        log.info("Finish main");
    }
    public static void getResult(Consumer<Integer> cb) {
        log.info("Start getResult");
        try {
            Thread.sleep(1000);
        } catch (InterruptedException e) {
            throw new RuntimeException();
        }

        var result = 0;
        cb.accpet(result);
        log.info("Finish getResult");
    }
}

 

  • caller는 callee의 결과에 관심이 없다.
    • main메소드는 gerResult메소드의 결과에 관심이 없다.
  • callee는 결과를 이용해서 callback을 수행한다.
    • gerResult메소드는 결과를 이용해서 함수형 인터페이스를 실행한다.
  • caller와 callee가 동기화되어있지 않다.

 

블로킹(Blocking)

 

  • callee를 호출한 후, callee가 완료되기 전까지 caller가 아무것도 할 수 없다.
  • 제어권을 callee가 가지고 있다.
  • caller와 다른 별도의 thread가 필요하지 않다. (혹은 thread를 추가로 쓸 수도 있다)

넌블로킹(Non-Blocking)

 

  • callee를 호출한 후, callee가 완료되지 않더라도 caller는 본인의 일을 할 수 있다.
  • 제어권을 caller가 가지고 있다.
  • caller와 다른 별도의 thread가 필요하다.

 

동기 블로킹 vs 비동기 블로킹

 

동기 넌블로킹 vs 비동기 넌블로킹

 

함수 호출 모델 정리

  동기 비동기
Blocking caller는 아무것도 할 수 없는 상태가 된다.
결과를 얻은 후 직접 처리한다.
caller는 아무것도 할 수 없는 상태가 된다.
결과는 callee가 처리한다.
Non-Blocking caller는 자기 할일을 할 수 있다.
결괄르 얻은 후 직접 처리한다.
caller는 자기 할 일을 할 수 있다.
결과는 callee가 처리한다.

 

 

 


 

※ 본 포스팅은 패스트캠퍼스 환급 챌린지 참여를 위해 작성하였습니다. https://bit.ly/48sS29N