2013-02-20 20 views
17

私は例外を投げるか、例えばContract.Requires<TException>例外と例外のスロー。<T>?

を呼ぶべきかどうか迷っています:

public static void Function(String str) 
{ 
    if (str == null) throw new ArgumentNullException("str", "Input string cannot be null."); 

    // ... 
} 

public static void Function(String str) 
{ 
    Contract.Requires<ArgumentNullException>(str != null, "Input string cannot be null."); 

    // ... 
} 

Contract.Requires<TException>CONTRACTS_FULLシンボルを必要としないので、私はそれを維持することができます私のリリースも構築されています。

これは私の考察です:

コン:あなたはカスタム例外型コンストラクタのオーバーロードされたバージョンを呼び出すことはできません。追加のパラメータをコンストラクタに渡す方法はありません。

プロ:静的ツールは、(たとえば、契約違反の呼び出し元に通知します)。

どのような状況で、どのような状況で使用する必要がありますか?

+0

「例外タイプのコンストラクタをオーバーロードする」とすれば、どんな利点がありますか? –

+3

@ PeterRitchie私は同じ理由でそれらのコンストラクタが存在すると仮定します。私はそれがより多くのデータ/情報を提供するので、私は推測する。 – MasterMastic

+1

例外タイプのオーバーロードに関するご質問がありません。また、Contract.Requires の使用法を誤解している可能性があります。そのオーバーロードを使用する場合は、リリースされたビットでツールを使用する必要があります。 CodeContractツールを使用してDLLを書き直さないと、期待したことができません。 –

答えて

7

CodeContractユーザーガイドに記載されているif-then-throwと​​の基本的なトレードオフは、リリースビットを使って構築する方法です。

ケース1if-then-throw、​​のみを使用してください。この場合、dll/exeで契約ツールを実行せずにリリースビットを構築することができます。利点は、ビルドが高速で、ツールがバグを導入するリスクがないことです。もう1つの利点は、チームメンバーがCodeContractツールの使用をオプトアウトできることです。デメリットは、必要なものの契約継承を取得しないことであり、契約書は必ずしもツールには表示されません(EndContractを使用しない限り)。このケースは、アセンブリモードを使用して指定します。カスタムパラメータの検証

ケース2:CodeContractツールは常にリリースビットで実行することにしました。これにより、​​を使用することができ、インタフェースの計測など、契約の継承を得ることができます。契約は清潔であり、ツールは認識可能です。欠点は、コードを作成するすべての人がCodeContractsツールをインストールしている必要があることです。この場合は、[契約]プロパティウィンドウの[アセンブリ]モード:[標準]を使用して指定します。

この明確な事柄を期待してください。

+0

VS2017を使用すると、CodeContractsツールを動作させるためのハックが発生する [VS2017はCodeContractsで動作しますか?](// stackoverflow.com/q/40767941) –

2

あなたが書いているようなコードは、非常にすっきりです)私は2つのアプローチのいずれかの驚天動地の違いがあることをわからないんだけど、ここで私は契約を好む理由は二つの理由...

1でありますその方法の基礎となる前提を示すステートメント。仮定が違反された場合に起こることの実装でコードを詰まらせることはありません。

2)コードを書くときにVisual Studioがコード契約を引き受けるという利点があります。また、呼び出すメソッドがどのようなことを期待しているかのヒントを提供します。これはメソッドの有効なパラメータを送信していることを確認するのに役立ちます。メソッド定義にジャンプしてコードをチェックする必要はありません。

コードをコンパイルして実行しても、大きな違いはないと思います。

これが役に立ちます。

+1

さらに2つの利点を追加します。 Contracts.Requiresは、ビルドシンボルを使用して簡単に「無効にする」ことができます(チェックが合格したことが確かな場合)。第二に(私はAvrohomには間違っていると思われる)VSには有効にできる静的コード分析エンジンがあり、(潜在的に)契約に違反するCALLINGコードのインスタンスを見つけることができます。 – Aron