回答編集履歴
8
検証コードを変更
answer
CHANGED
@@ -1,24 +1,25 @@
|
|
1
1
|
- task3 の foo 内に await が無い為、main側でawait した時点でタスクが作成順に実行されている。
|
2
|
-
- ~~bar() 関数は task4 を返すので
|
2
|
+
- ~~bar() 関数は task4 を返すので bar() は task4 を返すコルーチン~~
|
3
|
-
task4 = await bar() の右辺を評価した時点で タスクは実行されてます。
|
3
|
+
~~task4 = await bar() の右辺を評価した時点で タスクは実行されてます。~~
|
4
4
|
|
5
5
|
```python
|
6
6
|
task4 = await bar() # bar()の処理を実行. task4をクリエイト. PENDING.
|
7
7
|
```
|
8
8
|
|
9
|
-
検証: 以降の `await task4` を追加したり削除しても結果は変わりません。
|
9
|
+
~~検証: 以降の `await task4` を追加したり削除しても結果は変わりません。
|
10
|
-
この時点の task4 は消化済みのタスクなので、何もしないで次の処理に移ります。
|
10
|
+
この時点の task4 は消化済みのタスクなので、何もしないで次の処理に移ります。~~
|
11
|
+
|
12
|
+
|
13
|
+
訂正: タスクの実行を検証
|
11
14
|
```diff
|
12
15
|
- await task4 # task4を実行.
|
13
|
-
|
16
|
+
- await task3 # task3を実行.
|
17
|
+
+ await asyncio.sleep(0) # task3, task4 が実行。await の右辺は何でもよい
|
18
|
+
# 実行コンテキストの切り替え、処理をイベントループに戻す
|
19
|
+
# → 実行可能なタスクが処理される
|
14
20
|
|
15
21
|
```
|
16
22
|
|
17
|
-
```diff
|
18
|
-
+ await task4 # task4を実行.
|
19
|
-
await task4 # task4を実行.
|
20
|
-
await task3 # task3を実行.
|
21
|
-
```
|
22
23
|
|
23
24
|
----
|
24
25
|
追記: 想定されている挙動 task3 を task4 後に遅らせたい場合は、
|
@@ -38,4 +39,8 @@
|
|
38
39
|
await でイベントループに処理が戻ったタイミングで、実行可能ならば実行されます。
|
39
40
|
|
40
41
|
foo,bar,baz のコルーチン内に await がない ということは、どれも 即実行可能なので、
|
41
|
-
その為、await 順ではなく、実行順序は作成順になります。
|
42
|
+
その為、await 順ではなく、実行順序は作成順になります。
|
43
|
+
|
44
|
+
----
|
45
|
+
- create_task() で Task() が作成され、
|
46
|
+
- タスクはコンストラクタ内でイベントループにスケジュールされます。
|
7
質問に対する回答を追記
answer
CHANGED
@@ -29,4 +29,13 @@
|
|
29
29
|
+ task3 = foo("task3")
|
30
30
|
```
|
31
31
|
|
32
|
-
※ この場合、変数名に task は適切でないので、別名に。
|
32
|
+
※ この場合、変数名に task は適切でないので、別名に。
|
33
|
+
|
34
|
+
----
|
35
|
+
> どうしてtask3がtask4よりも先に実行されるのか。
|
36
|
+
|
37
|
+
タスクは、作成時に イベントループにスケジュールされ、
|
38
|
+
await でイベントループに処理が戻ったタイミングで、実行可能ならば実行されます。
|
39
|
+
|
40
|
+
foo,bar,baz のコルーチン内に await がない ということは、どれも 即実行可能なので、
|
41
|
+
その為、await 順ではなく、実行順序は作成順になります。
|
6
コードの整理
answer
CHANGED
@@ -26,7 +26,7 @@
|
|
26
26
|
|
27
27
|
```diff
|
28
28
|
- task3 = asyncio.create_task(foo("task3"))
|
29
|
-
+ task3 = foo("task3")
|
29
|
+
+ task3 = foo("task3")
|
30
30
|
```
|
31
31
|
|
32
32
|
※ この場合、変数名に task は適切でないので、別名に。
|
5
想定する挙動を追記
answer
CHANGED
@@ -18,4 +18,15 @@
|
|
18
18
|
+ await task4 # task4を実行.
|
19
19
|
await task4 # task4を実行.
|
20
20
|
await task3 # task3を実行.
|
21
|
-
```
|
21
|
+
```
|
22
|
+
|
23
|
+
----
|
24
|
+
追記: 想定されている挙動 task3 を task4 後に遅らせたい場合は、
|
25
|
+
恐らく、タスクではなくコルーチン
|
26
|
+
|
27
|
+
```diff
|
28
|
+
- task3 = asyncio.create_task(foo("task3"))
|
29
|
+
+ task3 = foo("task3") # task3をクリエイト. PENDING.
|
30
|
+
```
|
31
|
+
|
32
|
+
※ この場合、変数名に task は適切でないので、別名に。
|
4
説明が正確でなかったので訂正
answer
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
- task3 の foo 内に await が無い為、main側でawait した時点でタスクが作成順に実行されている。
|
2
|
-
- bar() 関数は task4 を返すので
|
2
|
+
- ~~bar() 関数は task4 を返すので~~ bar() は task4 を返すコルーチン
|
3
|
-
task4 = await bar() の右辺を評価した時点で
|
3
|
+
task4 = await bar() の右辺を評価した時点で タスクは実行されてます。
|
4
4
|
|
5
5
|
```python
|
6
6
|
task4 = await bar() # bar()の処理を実行. task4をクリエイト. PENDING.
|
3
文章補足
answer
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
- task3 の foo 内に await が無い為、await
|
1
|
+
- task3 の foo 内に await が無い為、main側でawait した時点でタスクが作成順に実行されている。
|
2
2
|
- bar() 関数は task4 を返すので
|
3
3
|
task4 = await bar() の右辺を評価した時点で task4 が実行されてます。
|
4
4
|
|
2
もうひとつの問題点を追記
answer
CHANGED
@@ -1,5 +1,5 @@
|
|
1
|
-
|
1
|
+
- task3 の foo 内に await が無い為、await の時点でタスクが作成順に実行されている。
|
2
|
-
|
2
|
+
- bar() 関数は task4 を返すので
|
3
3
|
task4 = await bar() の右辺を評価した時点で task4 が実行されてます。
|
4
4
|
|
5
5
|
```python
|
1
訂正
answer
CHANGED
@@ -18,13 +18,4 @@
|
|
18
18
|
+ await task4 # task4を実行.
|
19
19
|
await task4 # task4を実行.
|
20
20
|
await task3 # task3を実行.
|
21
|
-
```
|
22
|
-
|
23
|
-
----
|
24
|
-
想定する順序の挙動にするには、bar() がそのまま task4 を返すようにします。
|
25
|
-
|
26
|
-
```diff
|
27
|
-
- task4 = await bar()
|
28
|
-
+ task4 = bar()
|
29
|
-
|
30
21
|
```
|