驚いたことに、私はこの主題について SO に関する以前の質問を 1 つしか見つけることができませんでした。私のアプローチについて、コミュニティの「信任投票」(またはそうでない!) を取得したいと思います。
私がそれを見る方法は次のとおりです。
Debug.Assert
あなたが期待することが真実であることを述べるために使用します。これは、環境を完全に制御している場合に使用されます。たとえば、事前条件と事後条件を検証する方法です。- 例外的な状況が発生した場合は例外を使用します。ファイル、データベース、ネットワークなどの外部リソースを扱うのは簡単です。しかし...
次のシナリオでは、少し曖昧になります。これは説明のみを目的とした不自然な例であることに注意してください。
パブリック プロパティ MyMode と method を持つクラス MyClass があるとしますGetSomeValueForCurrentMode()
。MyClass は、他の開発者が使用するライブラリで出荷 (リリース ビルド) されることを意図したものと考えてください。
MyMode は、このクラスの外部ユーザーによって更新されることを期待しています。現在、GetSomeValueForCurrentMode()
次のロジックがあります。
switch(MyMode)
{
case Mode.ModeA:
return val1;
case Mode.ModeB:
return val2;
default:
//Uh-uh this should never happen
}
ここで私が得ているのは、MyClass のユーザーがそれを無効な状態のままにしたということです。だから何をすべきか?
デフォルトでは、私たちDebug.Assert
またはthrow new InvalidOperationException
(または他の)べきですか?
クラスのユーザーを信頼してはならないという 1 つのマントラがあります。Debug.Assert を選択し、MyClass をリリース ビルドとしてビルドした場合 (それによってデバッグ アサートを削除した場合)、クラスのユーザーは、クラスを無効な状態のままにしておいたという有用な情報を取得できません。しかし、それは、完全に制御できないことが起こった場合にのみ例外をスローするという別のマントラに反するものです。
私はこれについてぐるぐる回っていることに気づきました - 決定的な「正しい」答えがないように見えるプログラミングの議論の1つです。それでは投票に入れましょう!
編集:関連する SO の質問 (アサーションまたは例外を使用した契約による設計? ) でこの応答に気付きました:
経験則として、自分自身のエラーをキャッチしようとするときはアサーションを使用し、他の人のエラーをキャッチしようとするときは例外を使用する必要があります。つまり、例外を使用して、パブリック API 関数の前提条件を確認し、システムの外部にあるデータを取得するたびに確認する必要があります。システム内部の関数またはデータにはアサートを使用する必要があります。
私にとって、これは理にかなっており、以下に概説する「アサートしてからスローする」手法と組み合わせることができます。
考えを歓迎します!