Swift

Closure 심화

GREEN.1229 2021. 4. 27. 18:11

안녕하세요. 그린입니다🟢

이번 포스팅에서는 클로저의 심화편으로 Completion Handler / Escaping Closure / Auto Closure에 대해 알아보겠습니다.

 

Completion Handler

 - 어떤 상황에서 일이 끝났을때 진행할 업무를 담당

 - 컴플리션 핸들러에 클로저를 적용시켜볼 수 있음

 

Completion Handler에서의 클로저 축약 과정

 1. VC.present(secondVC, animated: true, completion: { () in print(“화면 이동”) })

 2. VC.present(secondVC, animated: true, completion: { print(“화면 이동”) })

 3. VC.present(secondVC, animated: true) { print(“화면 이동”) }

 

Escaping Closer

 - @escaping이라는 키워드를 붙여줌

 - Escape는 함수가 리턴되고 실행되는것을 의미

 - 함수 전달인자로 전달된 클로저가 함수 종료후 호출 시 함수를 탈출

 - 함수 사이 실행 순서를 조정할 수 있음

 - 비동기 작업에서 많이 사용

 - @escaping 키워드가 없다면 기본적으로 비탈출 클로저로 동작 (동작 후 사용할 필요가 없음)

 

Alamofire 서버 통신에서의 Escaping Closer예시

Alamofire.request(urlRequest).responseJSON { response in
  // handle response
}

@discardableResult
    public func responseJSON(
        queue: DispatchQueue? = nil,
        options: JSONSerialization.ReadingOptions = .allowFragments,
        completionHandler: @escaping (DataResponse<Any>) -> Void)
        -> Self
    {

    }

 --> 이스케이핑이 붙어 함수가 반환되고 실행됨으로 요청 후 결과를 기다린 후 응답함

 

Auto Closure

 - 자동 클로저로 함수 전달인자로 전달된 표현을 자동으로 변환

 - 전달인자를 갖고 있지 않음

 - 호출 시 감싸고 있는 코드의 리턴값을 반환

 - 실제로 사용될 때 지연되어 호출 (메모리의 지연이 발생할 수 있음)

 

Auto Closure 예시

func serve(customer customerProvider: () -> String) {
	print("\(customerProvider())!")
}
serve(customer: { customersInLine.remove(at: 0) } )

  -> 위와 같이 인자가없고 실제 사용될때 호출되어 반영됨

 

[느낀점]

클로저에 대해 항상 막막한 부분이 있었다. 함축 표현도 많기에 어디가 어떻게 클로저로 구현된거지? 이런 두려움이 있었다. 그러다보니 자연스레 클로저를 잘 사용하지 않게되고 서버 통신을 할때 많이 사용되는 비동기 작업에서 클로저로 구현된 부분에 대한 이해도 떨어졌다. 그래서 클로저를 심화적으로 더 익혀보려고 학습하였다. 클로저가 그렇게 막연한것은 아니라고 느껴졌다. 클로저는 정말 간단하게 이름없는 함수로 전달인자로도 반환으로도 사용될 수 있는것으로 형태의 낯설음이 점점 사라졌다. 실제 클로저에 대해 한걸음 다가서니 이벤트 핸들러 시 동작하는 원리와 비동기 처리에서 왜 해당 응답이 요청 후 기다렸다 되는지도 구조를 좀 더 쉽게 이해할 수 있었다.

 

[참고자료]

https://jusung.gitbook.io/the-swift-language-guide/language-guide/07-closures

https://duwjdtn11.tistory.com/520

https://hcn1519.github.io/articles/2017-09/swift_escaping_closure