2012-03-13 9 views
6

は私がテストを実行している指標で異なりますが、失敗した場合、私はなぜ知らない:あなたが見ることができるような値が同一であるNUnit。値は、[0]

Proj.Tests.StatTests.GetResults_RegularPage_ReturnListOfResults: 
    Expected and actual are both <System.Collections.Generic.List`1[Proj.Classes.StatResult]> with 50 elements 
    Values differ at index [0] 
    Expected: <test;98318> 
    But was: <test;98318> 

。 はここにいくつかのコードです:

public class StatResult 
    { 
     public string word { get; set; } 
     public UInt64 views { get; set; } 

     public override string ToString() 
     { 
      return String.Format("{0};{1}", word, views);     
     } 
    }  

    [Test] 
    public void GetResults_RegularPage_ReturnListOfResults() 
    { 
     // Arrange    
     WordStat instance = new WordStat(Constants.WordStatRegularPage); 
     // Act 
     List<StatResult> results = instance.GetResults(); 
     // Assert 
     Assert.AreEqual(results, new List<StatResult> 
     { 
      new WordStatResult { word ="test", views = 98318}, 
      new WordStatResult { word ="test board", views = 7801}, 
      //... I shorted it 
     } 

}

私は多くの方法でも右のクラスに、試験試料を入れてみましたが、それはとにかく動作しません。 助けてください!

+2

'WordStatResult'の' equal'演算子をオーバーロードするべきではありませんか? –

答えて

5

私は、2つの参照が等しいプロパティを持つオブジェクトを参照していることがわかりますが、ここではテストされていません。 同じオブジェクトへの参照か等しいかどうかを確認しています。 StatResultクラスはEquals/GetHashCodeをオーバーライドしないので、同じ値を持つ2つのオブジェクトとなり、テストでは「異なる」とみなされます。

2つのオブジェクトが適切に等しいとみなされるように、EqualsGetHashCodeを上書きする必要があります。私はまた性質のために、通常の.NET命名規則をタイプは不変作るだけでなく、以下のことをお勧めしたい:

public sealed class StatResult : IEquatable<StatResult> 
{ 
    public string Word { get; private set; } 
    public UInt64 Views { get; private set; } 

    public StatResult(string word, ulong views) 
    { 
     this.word = word; 
     this.views = views; 
    } 

    public override string ToString() 
    { 
     return String.Format("{0};{1}", word, views);     
    } 

    public override int GetHashCode() 
    { 
     int hash = 23; 
     hash = hash * 31 + Word == null ? 0 : Word.GetHashCode(); 
     hash = hash * 31 + Views.GetHashCode(); 
     return hash; 
    } 

    public override bool Equals(object other) 
    { 
     return Equals(other as StatResult); 
    } 

    public bool Equals(StatResult other) 
    { 
     return other != null && 
       this.Word == other.Word && 
       this.Views == other.Views; 
    } 
} 

あなたの建設だけで変化するであろうに:本番でも同様に

new StatResult("test", 98318), 
new StatResult("test board", 7801), 

(とコード)。

+0

不変性の詳細については同意できません。これはデフォルトで一般的に行うべきことですが、無視する/忘れる傾向があります。 – Randolpho

+0

ブリリアント!もう一度ジョンに感謝します。 – kseen

7

問題は、NUnitが2つのインスタンスStatResultの等価性をテストする方法です。等価比較演算子を実装していないため、等価性検査のデフォルトはインスタンスの参照になります。それらは2つの異なるインスタンスであるため、それらの参照は異なります。

オブジェクトに等価性を実装する方法の詳細は、this articleを参照してください。

1

Equals()とGetHashCode()をオーバーライドする必要があります。現時点では、各リストの最初の項目が同じオブジェクトへの参照かどうかを確認しています。

+0

しかしそれはクラスをひどく変えてしまいます。 –