Sendable 프로토콜은 객체가 concurrent code에서 안전하게 사용될 수 있다는 것을 명시합니다
Sendable이란?
Sendable은 특정 타입이 여러 스레드 간 안전하게 전달될 수 있음을 나타냅니다. 이 프로토콜을 준수하면, 해당 타입의 인스턴스가 여러 스레드 간에 전달될 때 data race이나 무결성 문제가 발생하지 않음을 보장합니다. 예를 들어, 값을 복사하거나 스레드 간에 참조를 공유할 때 안전하게 사용할 수 있습니다.
int, string과 같은 대부분의 기본 값 타입들은 기본적으로 Sendable을 준수합니다.
let number: Int = 42 // Int는 기본적으로 Sendable
Sendable 프로토콜을 준수하는 사용자 정의 타입
만일 사용자가 정의한 타입이 Sendable을 준수하려면 해당 타입의 모든 프로퍼티가 Sendable을 준수해야 합니다.
struct MyStruct: Sendable {
var value: Int // Int는 Sendable
}
let myStruct = MyStruct(value: 10)
Sendable 프로토콜을 준수하는 Class
Sendable은 특정 타입이 여러 스레드 간 안전하게 전달될 수 있음을 나타낸다고 했습니다, 이때 struct는 value type으로 해당 값을 접근하기 위해서는 새로운 변수를 만들어내기 때문에 스레드 간 데이터 무결성 문제가 발생하지 않습니다(참조하는 것이 아니라 기존 값이 바뀌지 않기 때문에)
하지만 class는 reference type이기 때문에 값을 복사해서 새롭게 만드는 대신에 Heap 메모리에 저장된 값을 변경하므로 무결성 문제가 발생하기 때문에 class는 기본적으로 Sendable을 준수하지 않습니다.
but 클래스 내부의 모든 프로퍼티가 Sendable을 준수한다면 클래스도 Sendable을 준수할 수 있을 것입니다, 그럼 모든 프로퍼티가 Sendable을 준수할 때 클래스를 Sendable로 선언해야 합니다.
추가로 final을 선언하여 final 클래스는 상속이 불가능하므로, 클래스의 동작이 예상치 못하게 변경될 가능성을 줄일 수 있습니다.
final class MyClassUserInfo: Sendable {
let name: String
init(name: String) {
self.name = name
}
}
Actor도 Sendable
actor는 concurrent code에서 data race를 피할 수 있도록 해줍니다, 다시 말해 actor는 기본적으로 동시성을 관리하고, 내부 상태의 스레드 안전성을 보장합니다, 따라서 actor의 메서드나 프로퍼티는 기본적으로 Sendable로 간주합니다.
actor MyActor {
var value: Int // Int는 Sendable
}
@unchecked Sendable
만약 변수의 값이 let이 아닌 var이지만 변경되지 않을 것이라는 점을 알 경우에는 다음처럼 @unchecked Sendable를 사용합니다.
하지만 이것은 컴파일러에게 코드를 체크하지 않아도 된다는 것을 의미하므로 사용할 때 매우 주의해야합니다.
final class MyClassUserInfo: @unchecked Sendable {
var name: String
init(name: String) {
self.name = name
}
}
결론
- Sendable 프로토콜은 value type과 reference type의 인스턴스가 여러 스레드 간에 안전하게 전달될 수 있음을 보장하는 중요한 역할을 합니다.
- 이는 concurrent 코드를 만들 때 data race 과 같은 문제를 방지하고, 안전하고 신뢰할 수 있는 코드를 작성할 수 있게 합니다.
'SwiftUI' 카테고리의 다른 글
AVFoundation 사용자가 말하는 동안만 녹음하기 (0) | 2024.05.31 |
---|---|
AVFoundation 이용한 음성 녹음하기 (0) | 2024.05.30 |
AsyncPublisher (.value로 비동기적으로 데이터 처리) (0) | 2024.05.25 |
MacPaw/OpenAI SwiftUI Package 분석하기 (0) | 2024.05.25 |
Global Actor과 Main Actor (0) | 2024.05.24 |