@@ -14,13 +14,21 @@ Tasks sent from a synchronous context to an asynchronous context in Swift Concur
1414
1515``` swift
1616@MainActor
17- func test_mainActor_taskOrdering () async {
18- var counter = 0
17+ func testMainActorTaskOrdering () async {
18+ actor Counter {
19+ func increment () -> Int {
20+ count += 1
21+ return count
22+ }
23+ var count = 0
24+ }
25+
26+ let counter = Counter ()
1927 var tasks = [Task< Void , Never > ]()
2028 for iteration in 1 ... 100 {
2129 tasks.append (Task {
22- counter += 1
23- XCTAssertEqual (counter , iteration) // often fails
30+ let incrementedCount = await counter. increment ()
31+ XCTAssertEqual (incrementedCount , iteration) // often fails
2432 })
2533 }
2634 for task in tasks {
@@ -51,14 +59,35 @@ queue.async {
5159 This task begins execution once the above one-second sleep completes.
5260 */
5361}
54- Task {
55- await queue.await {
56- /*
57- `async` context that can return a value or throw an error.
58- Executes after all other enqueued work is completed.
59- Work enqueued after this task will wait for this task to complete.
60- */
62+ await queue.await {
63+ /*
64+ `async` context that can return a value or throw an error.
65+ Executes after all other enqueued work is completed.
66+ Work enqueued after this task will wait for this task to complete.
67+ */
68+ }
69+ ```
70+
71+ With a ` FIFOQueue ` you can easily execute asynchronous tasks from a nonisolated context in FIFO order:
72+ ``` swift
73+ func testFIFOQueueOrdering () async {
74+ actor Counter {
75+ func increment () -> Int {
76+ count += 1
77+ return count
78+ }
79+ var count = 0
80+ }
81+
82+ let counter = Counter ()
83+ let queue = FIFOQueue ()
84+ for iteration in 1 ... 100 {
85+ queue.async {
86+ let incrementedCount = await counter.increment ()
87+ XCTAssertEqual (incrementedCount, iteration) // always succeeds
88+ }
6189 }
90+ await queue.await { }
6291}
6392```
6493
@@ -80,14 +109,35 @@ queue.async {
80109 This task begins execution once the above task suspends due to the one-second sleep.
81110 */
82111}
83- Task {
84- await queue.await {
85- /*
86- `async` context that can return a value or throw an error.
87- Executes after all other enqueued work has begun executing.
88- Work enqueued after this task will wait for this task to complete or suspend.
89- */
112+ await queue.await {
113+ /*
114+ `async` context that can return a value or throw an error.
115+ Executes after all other enqueued work has begun executing.
116+ Work enqueued after this task will wait for this task to complete or suspend.
117+ */
118+ }
119+ ```
120+
121+ With an ` ActorQueue ` you can easily begin execution of asynchronous tasks from a nonisolated context in order:
122+ ``` swift
123+ func testActorQueueOrdering () async {
124+ actor Counter {
125+ func increment () -> Int {
126+ count += 1
127+ return count
128+ }
129+ var count = 0
130+ }
131+
132+ let counter = Counter ()
133+ let queue = ActorQueue ()
134+ for iteration in 1 ... 100 {
135+ queue.async {
136+ let incrementedCount = await counter.increment ()
137+ XCTAssertEqual (incrementedCount, iteration) // always succeeds
138+ }
90139 }
140+ await queue.await { }
91141}
92142```
93143
0 commit comments