2016-09-01 15 views
0

keyは、ResharperがNULLでないことを知っていなくても、keyの最後の2つの参照にResharperによってフラグが立てられます。Resharper - Nullを非nullに割り当てる可能性のある偽陽性の属性

最初に、Null、空または空白の文字列プロパティがチェックされ、これらの条件のいずれかが該当する場合、ブロックはスキップされます。拡張メソッドToLowerNullSafe()は、入力がNULLの場合にのみNullを返します。これはAnnotation(2番目のコードブロック)でマークされます。プロパティがnullでなく、拡張メソッドがnull以外を返すようにマークされているので、Resharperはkeyがnullではないことを知っていると思います。

var myObj = new { MyProperty = "some string" }; 
var myCache = new Dictionary<string, object>(); 

if (!string.IsNullOrWhiteSpace(myObj.MyProperty)) 
{ 
    string key = myObj.MyProperty.ToLowerNullSafe(); 
    lock (myCache) 
    { 
     if (!myCache.ContainsKey(key)) 
     { 
      myCache.Add(key, myObj); 
     } 
    } 
} 

keyのフラグが設定されている場合、上記これらの2行は次のとおりここ

if (!myCache.ContainsKey(key)) 

myCache.Add(key, myObj); 

は、その注釈付きToLowerNullSafe方法、です。

[ContractAnnotation("null => null; notnull => notnull")] 
public static string ToLowerNullSafe(this string str) 
{ 
    return string.IsNullOrWhiteSpace(str) ? str : str.ToLower(); 
} 

ReSharperのは、注釈を無視しているように見える理由は上の任意のアイデア?そして私はそれをどのように修正するのですか?

使用:

  • Visual Studioの究極の2013アップデート5
  • ReSharperのNuget(コードおよび外部の両方)から8.2.3
  • 現在の注釈は、プロジェクトに適用されます。
  • 純4.5.2

EDIT

冗長ヌル!string.IsNullOrWhiteSpaceチェックがエラーをクリアする前または後のいずれかの冗長ヌルチェック(myObj.MyProperty != null)を追加myObj.MyProperty の確認。

if (myObj.MyProperty != null && !string.IsNullOrWhiteSpace(myObj.MyProperty)) 
{ 
    string key = myObj.MyProperty.ToLowerNullSafe(); 
    lock (myCache) 
    { 
     if (!myCache.ContainsKey(key)) 
     { 
      myCache.Add(key, myObj); 
     } 
    } 
} 

冗長ヌル冗長チェック、アサーション、または契約の仮定を追加すると、エラーをクリアすることができますkey に確認してください。

ここでは、keyに値を割り当てた直後にContract.Assume(key != null);を追加しました。

if (!string.IsNullOrWhiteSpace(myObj.MyProperty)) 
{ 
    string key = myObj.MyProperty.ToLowerNullSafe(); 
    Contract.Assume(key != null); 
    lock (myCache) 
    { 
     if (!myCache.ContainsKey(key)) 
     { 
      myCache.Add(key, myObj); 
     } 
    } 
} 

これもエラーをクリアしToLowerNullSafe を呼び出すことはありません。しかし、ContainsKeyメソッドは大文字と小文字を区別しない比較を行う場合に大文字と小文字を区別した比較を実行するため、問題が発生する可能性があります。

if (!string.IsNullOrWhiteSpace(myObj.MyProperty)) 
{ 
    string key = myObj.MyProperty; 
    lock (myCache) 
    { 
     if (!myCache.ContainsKey(key)) 
     { 
      myCache.Add(key, myObj); 
     } 
    } 
} 

は、組み込みの文字列関数ToLower を呼び出すまた、これはエラーをクリアします。しかし、コードベースに矛盾が生じます。ヌル値が予想され、安全に処理されなければならないコードには多くの場所があります。問題を避けるために、コード全体でカスタム...NullSafe拡張メソッドを適用しました。それが「ベストプラクティス」と一致するかどうかはわかりませんが、このプロジェクトで行っていることです。すべての作業のコード例では

if (!string.IsNullOrWhiteSpace(myObj.MyProperty)) 
{ 
    string key = myObj.MyProperty.ToLower(); 
    lock (myCache) 
    { 
     if (!myCache.ContainsKey(key)) 
     { 
      myCache.Add(key, myObj); 
     } 
    } 
} 

、ReSharperのは、単にToLowerNullSafe拡張メソッドに契約注釈を無視しているようです。しかし、最初の実例では、であるが、オブジェクトのプロパティに対して明示的で冗長なヌルチェックを使用することによって認識されます。

+1

これとは別に、大文字と小文字を区別するデフォルトの比較文字ではなく、大文字と小文字を区別しない文字列比較文字を使用して辞書を作成すると便利です。その後、「ToLower」に電話する必要はありません。 [このような質問はこちら]を参照してください。(http://stackoverflow.com/questions/13230414/case-insensitive-access-for-generic-dictionary) – citizenmatt

+0

@citizenmatt私はその提案を調査する必要があります。 – Zarepheth

答えて

2

あなたは、これが

[ContractAnnotation("str:null => null; str:notnull=>notnull")] 

ReSharperのは、この操作を行うと、このpageが、それはまた、ReSharperのからのバージョンの問題かもしれない見つけなぜ私が探していた試してみることができますか?

編集

私はあなたと同じように実装し、正確にあなたのコードから拡張メソッドを作って、私は注釈で次の操作を実行したときに波線「キー」に消えています。

[ContractAnnotation("null => true; notnull => true")] 

+0

パラメータが1つしかないので、パラメータ名もオプションです。とにかく、私はあなたの提案を試みましたが、何の違いもありませんでした。 – Zarepheth

+0

重要かどうかわかりませんが、拡張メソッドはソリューションの別のプロジェクトにあります。どちらのプロジェクトもResharper、Resharperコードアノテーション、Resharper外部アノテーションと同じバージョンを持っています。 Resharperのデフォルトの外部注釈は 'string.IsNullOrWhiteSpace'呼び出しを認識するべきですが、' ContractAnnotation 'の使用は 'ToLowerNullSafe'メソッドで認識されるべきです。 – Zarepheth

+0

なぜ私はそれが正しく今言っている場合、ContainsKeyがboolを返すので、同じことをやっている注釈が返ってくると思います。また、これらのことを今でも学んでいます... :) –

1

これはReSharper 8のバグだと思っています(特に、@ sarel-louwの回答が返され、文字列戻りのためにboolが返されます)。 ReSharper 2016.2でこれを試したところ、keyという変数にはフラグがつけられていません。ContractAnnotationは必要ありません。

+0

管理者がアップグレードのための資金を提供することを決めるまで(またはもっと良いフル・サブスクリプション)、私はReSharper 8.2.3に固執しています。 – Zarepheth

関連する問題