プログラム学習室 http://studyhallweb.com/

Dart言語: future 非同期処理

future そのものの説明については他のサイトに任せるとして、ここでは具体的な使用例をあげます。
そのほうが自分自身も分かりやすく再利用がしやすいものですから。

非同期処理が終わった後の処理 (ファイルを読み込んだ後の処理)

一般的にファイルの読み込みは非同期処理になります。
ファイルを読み込んだ後(futureの処理が終わった後)の処理は then() で指定します。
そうしないと思ったとおりの順番で処理できません。

page031_1dart.txt

上のプログラムを実行したとき、出力は次のようになります。

プログラム上では 007行('readFile始まり')、012行(then(_view))、017行('readFile 終わり') の順番になっていますが、 実行順は 'readFile 終わり'が先で、その後に _view() が実行されています。
ファイル読み込みの処理と同じメソッド(上の例では readFile)の中では、ファイル読み込みの後に続けて処理されません。 ファイルを読み込んだ後の処理は then() で指定したメソッド (上の例では _view) にコーディングすることになります。

非同期処理を順番どおりに行いたいとき (1つのファイルを読み込んでから、次のファイルを読み込む)

非同期処理が終わった後の処理は then() で指定すればよいことは分かりました。では、非同期処理を順番どおりに行いたいときは、どうすれば良いのでしょうか。
初めの then() で次のファイルを読み込む処理を書けばよいのです。

初めのファイル読み込み.then(次のファイル読み込み)
次のファイル読み込み.then(読み込んだ後の処理)

あまり美しくはないですが、上記のようになります。
2つくらいでしたらまだよいのですが、これを繰り返すと初めのファイル読み込みから読み込んだ後の処理への見通しが悪くなります。 そこで、次のように then() を続けて書くことも出来ます。

初めのファイル読み込み
.then(次のファイル読み込み)
.then(読み込んだ後の処理)

この例を次に示します。
page031_2dart.txt

012行で、HttpRequest.getString() で読み込んだテキストは 013行で _readFilePlus() に引数として渡されます。
_readFilePlus() はファンクションになっていて、その中で読み込んだテキストを戻り値として返しています(029行)。
それを014行で readText2 として受け取り、_view() に渡しています。

この実行結果は次のようになります。
012行で呼んだファイルの中身(大文字)に、013行で呼んだ中身(小文字)を、014行の処理で追加して表示しています。

複数の非同期処理が終わるのを待って次の処理を行う (2つのファイルを読み込んでから処理をする)

複数の非同期処理が終わってから次の処理を行いたいときは wait() を使います。
Futuer.wait([非同期処理1, 非同期処理2,, ])].then(非同期処理が終わってからの処理)

この例を次に示します。
page031_3dart.txt

011, 012行が複数の非同期処理が終わってから次の処理を行っているところになります。
_readFile1() と _readFile2() の戻り値String を List<String> として受け取り、_view3() に渡しています。

この実行結果は次のようになります。(上の例とは逆に、ファイル2の内容にファイル1の内容を加えて表示しています)