So vergleichen Sie Listen in Unit-Tests


180

Wie kann dieser Test fehlschlagen?

[TestMethod]
public void Get_Code()
{
    var expected = new List<int>();
    expected.AddRange(new [] { 100, 400, 200, 900, 2300, 1900 });

    var actual = new List<int>();
    actual.AddRange(new [] { 100, 400, 200, 900, 2300, 1900 });

    Assert.AreEqual(expected, actual);
    // Assert.AreSame(expected, actual)       fails
    // Assert.IsTrue(expected.Equals(actual)) fails
}

Antworten:


370

Um Aussagen über Sammlungen zu machen, sollten Sie Folgendes verwenden CollectionAssert:

CollectionAssert.AreEqual(expected, actual);

List<T>wird nicht überschrieben Equals. Wenn also Assert.AreEqualnur aufgerufen wird Equals, wird die Referenzgleichheit verwendet.


6
Ich wünschte, dies würde detailliertere Nachrichten geben, wenn es fehlschlug. "Unterschiedliche Anzahl von Elementen" und "Element bei Index 0 stimmen nicht überein" sind leicht nutzlos. Was sind sie dann?!
Colonel Panic

32
Wenn Sie sich nicht für die ArtikelreihenfolgeCollectionAssert.AreEquivalent
interessieren

2
Beachten Sie, CollectionAssert.AreEqualdass spürbar langsamer sein kann alsAssert.IsTrue...SequenceEqual
Mark Sowul

1
@ MarkSowul: Aber es kommt mit einer viel besseren Fehlerdiagnose, oder?
Jon Skeet

2
@ MarkSowul: Hmm ... hört sich so an, als wäre es wert, als Fehler gemeldet zu werden. Kein Grund, warum es so schlimm sein sollte.
Jon Skeet

34

Ich denke, das wird helfen

Assert.IsTrue(expected.SequenceEqual(actual));

4
Das war auch mein Rückfall, aber ich hoffe, dass CollectionAssert hilfreichere Fehlermeldungen liefert.
Jon Skeet

4
Leider nicht wirklich: "CollectionAssert.AreEqual fehlgeschlagen. (Element bei Index 0 stimmt nicht überein.)" (Was sind die Elemente?)
Namey

17

Wenn Sie überprüfen möchten, ob jede dieselbe Auflistung von Werten enthält, sollten Sie Folgendes verwenden:

CollectionAssert.AreEquivalent(expected, actual);

Bearbeiten:

"Zwei Sammlungen sind äquivalent, wenn sie dieselben Elemente in derselben Menge, aber in beliebiger Reihenfolge haben. Elemente sind gleich, wenn ihre Werte gleich sind, nicht wenn sie sich auf dasselbe Objekt beziehen." - https://msdn.microsoft.com/en-us/library/ms243779.aspx


14

Ich habe die anderen Antworten in diesem Thread ausprobiert und sie haben bei mir nicht funktioniert. Ich habe Sammlungen von Objekten verglichen, in deren Eigenschaften dieselben Werte gespeichert waren, die Objekte jedoch unterschiedlich waren.

Methodenaufruf:

CompareIEnumerable(to, emailDeserialized.ToIndividual,
            (x, y) => x.ToName == y.ToName && x.ToEmailAddress == y.ToEmailAddress);

Vergleichsmethode:

private static void CompareIEnumerable<T>(IEnumerable<T> one, IEnumerable<T> two, Func<T, T, bool> comparisonFunction)
    {
        var oneArray = one as T[] ?? one.ToArray();
        var twoArray = two as T[] ?? two.ToArray();

        if (oneArray.Length != twoArray.Length)
        {
            Assert.Fail("Collections are not same length");
        }

        for (int i = 0; i < oneArray.Length; i++)
        {
            var isEqual = comparisonFunction(oneArray[i], twoArray[i]);
            Assert.IsTrue(isEqual);
        }
    }

3
Netter Zusatz, oder Sie können auch die EqualsMethode überschreiben und das CollectionAssertwird funktionieren.
Ray Cheng

6

Dieser Test vergleicht eine Datumseingabe und prüft, ob es sich um ein Schaltjahr handelt. Wenn ja, werden 20 Schaltjahre vom eingegebenen Datum ausgegeben. Wenn nicht, werden die NÄCHSTEN 20 Schaltjahre ausgegeben, myTest.Testing bezieht sich auf die myTest-Instanz, die wiederum die Werte aufruft aus einer Liste namens Testing, die die erforderlichen berechneten Werte enthält. Teil einer Übung, die ich machen musste.

[TestMethod]
        public void TestMethod1()
        {
            int testVal = 2012;
            TestClass myTest = new TestClass();
            var expected = new List<int>();
            expected.Add(2012);
            expected.Add(2016);
            expected.Add(2020);
            expected.Add(2024);
            expected.Add(2028);
            expected.Add(2032);
            expected.Add(2036);
            expected.Add(2040);
            expected.Add(2044);
            expected.Add(2048);
            expected.Add(2052);
            expected.Add(2056);
            expected.Add(2060);
            expected.Add(2064);
            expected.Add(2068);
            expected.Add(2072);
            expected.Add(2076);
            expected.Add(2080);
            expected.Add(2084);
            expected.Add(2088);
            var actual = myTest.Testing(2012);
            CollectionAssert.AreEqual(expected, actual);
        }

0
List<AdminUser> adminDetailsExpected = new List<AdminUser>()
{
new AdminUser  {firstName = "test1" , lastName = "test1" , userId = 
"001test1"  },
new AdminUser {firstName = "test2" , lastName = "test2" , userId = 
"002test2"   }
};

//Handlung

List<AdminUser> adminDetailsActual = RetrieveAdmin(); // your retrieve logic goes here

//Behaupten

Assert.AreEqual(adminDetailsExpected.Count, adminDetailsActual.Count);  //Test succeeds if the count matches else fails. This count can be used as a work around to test

0

Fließende Behauptungen führen tiefe Vergleiche von Arrays durch actualArray.Should().BeEquivalentTo(expectedArray)

Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.