Actorの分離とnonisolated
分離の境界について考えます。
「Actorの分離とnonisolated」はCoddyKit上の無料Swift Academyレッスンです。 これはレッスン3/4です。 下記で完全なレッスンを無料で読むことができます。その後、ブラウザ内の組み込みコードエディタと24時間対応のAIチューターでハンズオン演習できます。 これはSwift Academy学習パスの一部であり、ウェブとCoddyKitアプリ全体で進捗が同期されます。 Swift Academyコースには全4レッスンが含まれています。
アクター分離とは
アクター分離とは、アクターの可変状態に触れられるのは、そのアクター上で実行されているコードだけであるという意味です。
ランタイムがアクセスを直列化するため、2つのタスクが状態を同時に変更することはなく、データ競合がなくなります。
actor Counter {
private var value = 0
func increment() { value += 1 }
}アクターの呼び出し
アクターの外部から分離されたメンバーにアクセスすると、呼び出しは非同期になります。アクターが空くまで呼び出しが中断する可能性があるため、awaitが必要です。
let counter = Counter()
func useCounter() async {
await counter.increment()
}アクター内部:同期実行
アクター自身のメソッド内ではすでに分離された状態にあるため、状態には同期的にアクセスできます。selfに対してはawaitは必要ありません。
actor Counter {
private var value = 0
func incrementTwice() {
value += 1 // synchronous: already isolated
value += 1
}
}nonisolatedメンバー
可変状態に触れないメンバーにはnonisolatedを付けます。このようなメンバーはどこからでも同期的に実行でき、awaitも必要ありません。
不変データだけから作られる計算プロパティに適しています。
actor User {
let id: Int
var sessionCount = 0
init(id: Int) { self.id = id }
nonisolated var label: String { "User #\(id)" }
}nonisolatedが安全な理由
nonisolatedメンバーが読み取れるのは、不変(let)の状態、またはそれ以外のSendableな状態だけです。
nonisolatedコンテキストから可変な分離状態にアクセスしようとすると、コンパイラーが拒否します。
actor User {
let id: Int
var sessionCount = 0
init(id: Int) { self.id = id }
// Error: cannot read mutable sessionCount here
// nonisolated var bad: Int { sessionCount }
}nonisolatedとプロトコル
アクターが同期的なプロトコルに適合するとき、nonisolatedは不可欠です。プロトコルのメソッドはasyncにできないため、分離された状態を使わないようにする必要があります。
actor Item: CustomStringConvertible {
let name: String
init(name: String) { self.name = name }
nonisolated var description: String { "Item: \(name)" }
}MainActor
@MainActorはコードをメインスレッドに分離するグローバルアクターです。UIの更新はここで行います。
型、メソッド、またはプロパティに注釈を付けて、メインアクター上で実行されるようにします。
@MainActor
final class ViewModel {
var title = "Hello"
func refresh() { title = "Updated" }
}アクター間の切り替え
あるアクターから別のアクターを呼び出すと、ランタイムはエグゼキューターを切り替え、処理を中断します。その中断がまさにawaitが現れる場所です。
actor Database { func load() -> Int { 42 } }
@MainActor
func show(_ db: Database) async {
let v = await db.load() // hop to db actor
print(v) // hop back to main
}アクターの再入可能性
アクターは再入可能です。メソッドがawaitすると、awaitから再開する前に、アクターがキューに入っている別の処理を実行することがあります。
awaitの前に読み取った状態は、awaitの後では変わっている可能性があります。中断ポイントの後で前提を再確認してください。
actor Store {
var ready = false
func prepare() async {
ready = false
await Task.yield() // other calls may run here
ready = true
}
}isolatedパラメーター
関数はisolatedなアクターパラメーターを受け取り、そのアクターのメンバーでなくても、関数本体をそのアクター上で実行できます。
func bump(on counter: isolated Counter) {
// runs isolated to counter; synchronous access
}サブシステム用のグローバルアクター
独自のグローバルアクターを定義して、サブシステム全体(たとえばレンダリングパイプライン)を1つのエグゼキューター上に分離できます。
@globalActor
actor RenderActor {
static let shared = RenderActor()
}
@RenderActor func draw() { }理解度チェック:分離
アクター分離についての理解度を確認しましょう。
まとめ:アクター分離とnonisolated
アクター分離は可変状態へのアクセスを直列化します。アクターをまたぐ呼び出しは非同期で、awaitが必要です。nonisolatedメンバーは分離から外れますが、不変またはSendableな状態だけを読み取ることができ、同期的なプロトコル適合に不可欠です。
@MainActorはコードをメインスレッドに固定し、アクターは再入可能であるためawaitの前後で状態が変わる可能性があります。また、グローバルアクターはサブシステム全体を分離します。これらのルールを理解することが、安全な並行処理の中心です。
AI チューターと学ぶ Swift — 無料
ブラウザでリアルコードを書いて実行し、24/7 の AI チューターから瞬時にサポートを受け、ウェブまたはアプリで続きから学習できます。
- コース
- 122
- レッスン
- 409
よくある質問
「Actorの分離とnonisolated」レッスンは無料ですか?
はい。「Actorの分離とnonisolated」の完全なテキストはこのウェブで無料で読めます。インタラクティブに演習し(組み込みコードエディタと24時間対応のAIチューター)、Swift Academyコースの残りをアンロックするには、CoddyKit PROにアップグレードしてください。 Swift Academyコースには全4レッスンが含まれています。
「Actorの分離とnonisolated」で何を学びますか?
分離の境界について考えます。 ブラウザで直接実行するハンズオンコードでSwift Academyを演習し、24時間対応のAIチューターがレッスンを進める中での質問に答えます。
Swift Academyを始めるのに経験は必要ですか?
事前経験は必要ありません。CoddyKitのSwift Academyは初級者から上級者向けに構成されているため、ここから始めるか最初から始めて、自分のペースで進むことができます。 これはレッスン3/4です。
「Actorの分離とnonisolated」レッスンにはどのくらい時間がかかりますか?
ほとんどのCoddyKitレッスンは約5~10分かかります。各レッスンはコンパクトでインタラクティブなので、着実に進歩し、ウェブとアプリ全体で正確に前回の場所から再開できます。
このSwift Academyレッスンでコードを書いて実行できますか?
はい。すべてのSwift Academyレッスンに組み込みコードエディタが含まれているため、ブラウザでリアルコードを書いて実行し、即座のAIフィードバックを取得できます。ローカル設定は不要です。
このコースのすべてのレッスン
- データ競合の問題
- Sendableプロトコル
- Actorの分離とnonisolated
- 厳密な並行性チェックへの移行