null
条件演算子?.
で安全に参照型にアクセスできるはず...
?.
を使うとnull
かもしれない参照型に安全にアクセスすることができます。
?.
はアクセスの前に、左辺がnull
かどうかテストしnull
でない場合、アクセスが行われます。
下記コードならhttpResponse.Content
がnull
でもnull
参照例外をスローしないと考えました。
HttpResponseMessage httpResponse = await this.httpClient.SendAsync(httpRequest);
// null かもしれない参照型の非同期メソッドを呼び出す
string content = await httpResponse.Content?.ReadAsStringAsync();
しかし、 Content
がnull
の場合、参照例外がスローされました。
System.NullReferenceException: Object reference not set to an instance of an object.
何が起こったか
?.
演算子は?.
の左辺がnull
の場合、null
が返します。
await httpResponse.Content?.ReadAsStringAsync();
Content
がnull
の時、null
をawait
してしまっています。
どう解決したか
??
(null
合体演算子)を使い、?.
がnull
を返した時にTask
を返すようにします。
今回はContent
がnull
の時は空文字が欲しかったので以下のようにしました。
HttpResponseMessage httpResponse = await this.httpClient.SendAsync(httpRequest);
// ※実行順序を正しくするため`await`する内容を`()`で囲む必要があります。
string content = await (httpResponse.Content?.ReadAsStringAsync() ?? Task.FromResult(string.Enmpty));
戻り値がない場合は、Task.CompleteTask
を使い以下のようにします。
await (this.FooService?.BarAsync() ?? Task.CompleteTask);
これでnull
かもしれない参照型の非同期メソッドを安全に呼び出すことができました。
結構見逃しやすい部分ですので注意したいと思います。