[문제해결] @Sendable과 isolated 실전 응용: AVCaptureDevice.requestAccess(for:)
·
📱 iOS/Swift Concurrency
문제해결final class CustomAlbumViewController: UIViewController { private func checkCameraAuthorization() { let authorization = AVCaptureDevice.authorizationStatus(for: .video) switch authorization { case .notDetermined: AVCaptureDevice.requestAccess(for: .video) { @Sendable granted in if granted { Task { [weak self] in ..
[Swift Concurrency 11편] Main Actor
·
📱 iOS/Swift Concurrency
특별한 Actor - Main ActorMain Thread & Main Actor우리의 메인 스레드는 UI 렌더링 및 사용자 이벤트가 처리되는 곳이다. 왜 메인 스레드에서 UI 렌더링 해야 하는지는 지난 번에 다뤄보았다.모든 작업을 메인 스레드에서 처리해버리면 UI 렌더링에 문제가 생겨 버벅일 수 있다.우리는 메인 스레드에서 실행해야 할 오래 걸리는 작업이 있으면 GCD Async를 통해 백그라운드로 보냈다. 그리고 그 코드는 메인 스레드에서 동작할 거다. 메인 스레드와 상호작용하는 것이 actor와 상호작용하는 것과 유사하다.메인 스레드에서 실행중이면 UI State에 안전하게 접근하여 업데이트, 메인 스레드가 아니라면 비동기로 스레드와 상호작용하는 원리 말이다. 메인 스레드를 나타내는 특별한 Glo..
[Swift Concurrency 10편] Actor는 한글 키보드로 'ㅁㅊ색' 이란 걸 아시나요?
·
📱 iOS/Swift Concurrency
개요지난 편에 이어서 이제 본격적으로 Actor라는 Object Type에 대해 알아보겠습니다.actor를 한글 키보드로 종종 잘못 치곤 하는데요, actor == ㅁㅊ색이라는 게 뭔가 잘 어울리네요 TaskTask는 독립적인 비동기 컨텍스트를 제공해줘서 비동기 메소드를 실행할 수 있는 공간이다.WWDC에서는 Task를 동시성의 바다 위에 떠다니는 보트로 비유한다.Task는 여러 개 생성할 수 있으며, 각각은 독립적이나 그 안에서의 데이터들은 값 타입인지 참조 타입인지에 따라 다르다. 참조 타입의 경우 아래 사진과 같이 독립적인 Task에서 내부적으로는 공유된 데이터를 사용할 수 있기에 이를 문제라 본다. 따라서 Task에서는 멀티 스레드에 의해 데이터 레이스가 발생할 수 있기 때문에 struct에서는 ..
[Swift Concurrency 9편] Sendable 프로토콜
·
📱 iOS/Swift Concurrency
Sendable 프로토콜비동기 컨텍스트에서 동작할 수 있도록 보장해주는 프로토콜값 타입의 경우 자동으로 채택레퍼런스인 클래스의 경우 채택해야 비동기 컨텍스트에서 데이터 경쟁 없이 동작하는 걸 컴파일러로부터 보장 받을 수 있음클래스가 Sendable을 채택하려면?아래 3가지를 따라야 함final 로 선언되어야 함프로퍼티가 모두 Sendable을 채택해야 함프로퍼티가 모두 let이어야 함 (불변이어야 한다는 뜻)actor는 Sendable을 채택하고 있음protocol Actor : AnyObject, [Sendable](https://developer.apple.com/documentation/swift/sendable>)Sendable을 채택할 수 있는 것들값 타입mutable storage 가 없는 참..
[Swift Concurrency 8편] Task와 구조화된 동시성(= Structed Concurrency)
·
📱 iOS/Swift Concurrency
Task 개념비동기 코드를 실행하기 위한 새로운 실행 컨텍스트를 제공함 async-await를 호출할 수 있게 하고, 병렬로 코드 실행을 지원하는 매커니즘우린 여태껏 async 호출을 통해 비동기 작업을 다뤘다.그러나 async를 사용한다고 해서 한 번에 둘 이상의 작업을 수행하지 않는다.async가 동시성을 제공하는 건 아니라는 뜻 Task는 코드를 병렬로 실행하게 하며 각 Task는 다른 Task와 동시에 실행할 수 있는 비동기 컨텍스트를 제공한다.Task로 생성된 작업은 MainActor가 아니라면 백그라운드 스레드에서 실행된다. await를 사용해서 완료된 값이 돌아올 때까지 기다릴 수 있음 하나의 Task 안에서 async 함수를 호출하고,그 안에서 또 async를 호출한다면 동일한 Task에서..
[Swift Concurrency 7편] 비동기 호출에서의 스레드 제어권
·
📱 iOS/Swift Concurrency
개요await로 비동기 메소드를 호출하는 경우, Potential Suspension Point로 지정된다. 생각해보면 당연하다await로 URLSession의 data 비동기 메소드를 호출하면 그 아래 작업들은 data 메소드가 끝날 때 까지 기다리게 된다. 이 지점을 Suspension Point 라고 한다.이를 통해 fetchThumbnail의 메소드는 더 이상 할 일이 없으니, 해당 작업을 처리하던 스레드가 다른 동작을 할 수 있게끔 제어권을 놓아주는 행위를 할 수 있다.스레드를 멈추는 것이 아닌, 다른 작업을 할 수 있게 제어권을 넘기는 것 말이다. Suspend 된다 = 해당 스레드에 대한 제어권을 포기한다라고 봐도 무방할듯스레드 제어권 관점sync 에서의 스레드 제어권A 함수에서 B라는 sy..
[Swift Concurrency 6편] Swift Concurrency 등장 배경
·
📱 iOS/Swift Concurrency
학습 목표Swift Concurrency 등장 이유Task 역할Swift Concurrency 소개(= 등장 배경)WWDC 2021년에 소개된 동시성 프로그래밍 APIasync와 await 키워드로 비동기 태스크 종료 후 코드를 작성할 수 있다.await로 중지되면, 이후 사용해야 하는 데이터를 Heap 영역에 저장하고, 이후 다시 돌아오면 꺼내서 사용한다.GCD와 비교하며 왜 등장하게 되었는지 살펴보겠다.가독성 & 에러처리 관점가독성기존의 GCD는 비동기 작업이 끝났는 지의 여부를 Completion Closure를 통해 알려준다.그러면 A 작업이 끝나면 B, B 작업이 끝나면 C, … 이를 비동기로 처리한다면 무수히 많은 Depth가 생겨 들여쓰기에 의해 가독성이 낮아질 것이다. 반면 Swift Co..
[Swift Concurrency 5편] 동시성 프로그래밍 with GCD
·
📱 iOS/Swift Concurrency
개요동시성 프로그래밍 이론동시성 프로그래밍: 여러 작업들을 동시에 처리하는 것처럼 보이게 하는 것이번 주는 동시성 프로그래밍과 이를 위한 기법 GCD를 배워보겠음(사진 날진님 블로그 제공)좌측에 있는 노동자 = Thread우측에 있는 일 = TaskURLSession.dataTask() 처럼 기본적으로 백그라운드 스레드에서 비동기로 실행되는 게 아니라면우리는 여태껏 메인 스레드에 Task를 할당 해주고 있었다.예를 들어 50MB 이미지를 Data 클래스로 변환하는 작업을 하더라도 그냥 메소드에서 변경하고 있었다면 이는 메인 스레드에서 작업하는 것.메인 스레드 역할메인 스레드는 UI를 그리는 일을 해야 한다.뷰 그리는 UIKit의 속성을 백그라운드에서 돌리기 위해 Thread-safe하게 하려면 성능저하가..
[Swift Concurrency 4편] 직렬-동시, 동기-비동기
·
📱 iOS/Swift Concurrency
동시(Concurrent) vs 직렬(Serial)동시(Concurrent): 여러 스레드로 작업을 분산시켜 보낸다.직렬(Serial): 하나의 스레드로만 작업들을 보낸다. (작업 순서가 중요할 경우)동기(Sycn) vs 비동기(Async)동기(Synchronous): 다른 스레드로 보낸 작업이 끝날때까지 기다린다.작업이 순차적으로 진행되며 작업을 대기하는 동안 CPU가 낭비된다는 특징이 있다.비동기(Asynchronous): 작업을 다른 스레드에서 시키고, 바로 내 할 일을 한다.작업 흐름이 복잡해질 수 있지만 다음 작업에 대한 대기 시간이 감소한다는 특징이 있다.병렬 vs 동시병렬(Parallel): 멀티 코어에서 멀티 스레드를 사용해 실제로(물리적으로) 여러 작업을 한 번에 실행시킨다.동시(Conc..
[Swift Concurrency 3편] 공유자원과 임계영역
·
📱 iOS/Swift Concurrency
공유자원각 프로세스, 스레드가 접근할 수 있는 자원 or 변수경쟁 조건공유 자원을 두 개 이상의 프로세스가 동시에 읽거나 쓰는 상황공유 데이터에 동시 접근하거나, 동시에 업데이트하려는 과정에서접근 순서에 따라 결과가 달라질 수 있는 현상을 이야기함임계영역경쟁 조건이 발생하는 코드 영역공유 자원을 접근하므로, 동시에 두 스레드가 실행해서는 안되는 코드원자적으로 수행되면 문제가 생기지 않음그러나, 쓰기 작업을 할 때 아래와 같이 3단계의 명령어로 구성되어 일관성 문제 발생 상호 배제 (Mutual Exclusion)반드시 하나의 스레드만 임계영역을 실행하도록 보장하는 기법임계영역을 해결하기 위한 방법 3가지뮤텍스 (= 락) 프로세스나 스레드가 공유자원을 Lock()으로 잠금 설정하고 락 소유권을 얻고..