비동기 함수를 병렬로 호출
await를 사용하여 비동기 함수를 호출하면 한 번에 하나의 코드만 실행
let firstPhoto = await downloadPhoto(named: photoNames[0])
let secondPhoto = await downloadPhoto(named: photoNames[1])
let thirdPhoto = await downloadPhoto(named: photoNames[2])
let photos = [firstPhoto, secondPhoto, thirdPhoto]
show(photos)
→ 이런 경우 downloadPhoto가 비동기 작업이어도 프로퍼티에 값을 넣는 동기 작업이 따르기 때문에 동기적으로 작업이 처리됨
async let firstPhoto = downloadPhoto(named: photoNames[0])
async let secondPhoto = downloadPhoto(named: photoNames[1])
async let thirdPhoto = downloadPhoto(named: photoNames[2])
let photos = await [firstPhoto, secondPhoto, thirdPhoto]
show(photos)
→ 비동기 함수를 호출하고 주위 코드와 병렬로 실행되기 위해선, async let을 사용하여 프로퍼티 값을 만드는 동작 전체를 비동기로 처리
→ async let과 await은 일시 중단되는 동안 다른 코드를 실행할 수 있음
→ 단, async-await 코드의 결과에 따라 달라지는 경우엔 순차적으로 진행해야하기 때문에, show는 let photos의 값이 생성된 후 동기적으로 실행
Continuation
- 처리가 완료된 비동기 메서드의 결과를 다시 시작(resuem)할 수 있는 기능
- Swift에서 높은 수준의 안전한 방법으로 Continuation을 생성, 관리, 재개할 수 있는 기능을 제공함
- 단, resume은 정확한 곳에서 한번 호출해야함
- API 비동기 호출을 수동으로 두번 시작하는 경우 모든 경로에서 resume을 호출해야함
- GCD보다 스위프트 컨커런시가 스레드 관리가 더 효율적이다
- → API중에서 스위프트 컨커런시를 지원하지 않는 경우 이렇게 감싸서 사용할 수 있다
- → 특정 상황에서 대리자 API가 여러 번 호출되거나 전혀 호출되지 않는 경우 active continuations을 정확히 한 번 다시 시작하는 것이 중요
Task & Task Groups
Task
- 프로그램의 일부
- 비동기적으로 실행할 수 있는 작업 단위
- Task의 이니셜라이저에 completionHander를 사용하여 동기화 컨텍스트 내부에서 다른 비동기를 호출 가능하게 함
- 클로저에서 작업을 패키지화하여 다른 스레드에서 즉시 실행 가능하도록 시스템에 보냄
- 모든 비동기 코드는 Task의 일부로써 실행됨
- → child Task을 생성할 수 있음
- → Task Group을 만들고 이에 child Task를 추가할 수 있음
- → Task Group을 사용하여 우선 순위를 설정하고 작업 취소를 보다 잘 제어할 수 있음
- → Task를 생성 시 Task의 갯수를 동적으로 지정할 수 있음
Structed Concurrency
- Task가 명시적인 계층 구조로 정렬되어있음
- 같은 parent Task를 갖은 Task의 묶음이 Task Group, 각 Task는 child Task를 가질 수 있음
- 명시적 계층 구조를 갖기 때문에 Swift가 일부 동작을 처리하며 컴파일 타임에서 오류를 감지 가능
// Task Group
await withTaskGroup(of: Data.self) { taskGroup in
// Task
let photoNames = await listPhotos(inGallery: "Summer Vacation")
for name in photoNames {
// child Task
taskGroup.addTask { await downloadPhoto(named: name) }
}
}
Task Group
- withTaskGroup(of:returning:body:)로 Task Group 생성
- Task 외부의 Task Group을 사용 금지→ child Task와 같은 동시성 작업에선 mutating한 작업을 수행할 수 없기 때문에, Task Group에서 escaping하는 것을 금지하는 것
- → Swift는 Task Group에 child Task를 추가하는 것은 mutating한 작업임
728x90
'학습활동' 카테고리의 다른 글
URL Loading System (0) | 2023.11.30 |
---|---|
동시성 프로그래밍 (0) | 2023.11.08 |
Swift Concurrency I (0) | 2023.09.28 |
User Notifications (0) | 2023.09.25 |
OAuth(Open Authorization) (0) | 2023.09.21 |