Como comparar listas em testes de unidade

181

Como esse teste pode falhar?

[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
}
Ray Cheng
fonte

Respostas:

371

Para fazer afirmações sobre coleções, você deve usar CollectionAssert:

CollectionAssert.AreEqual(expected, actual);

List<T>não substitui Equals, portanto, se Assert.AreEqualapenas chamar Equals, ele acabará usando a igualdade de referência.

Jon Skeet
fonte
6
Eu gostaria que isso desse mensagens mais detalhadas quando falhou. "Número diferente de elementos" e "Elemento no índice 0 não coincidem" são um pouco inúteis. O que eles são então ?!
Coronel Panic
32
Se você não se preocupam com ordem dos itens: {A, B, C} == {C, B, A}, em seguida, usar CollectionAssert.AreEquivalentem vez msdn.microsoft.com/en-us/library/ms243779.aspx
user2023861
2
Observe que CollectionAssert.AreEqualpode ser visivelmente mais lento que o #Assert.IsTrue...SequenceEqual
Mark Sowul 17/10
1
@ MarkSowul: Mas ele vem com um diagnóstico de falha muito melhor, certo?
21816 Jon Skeet
2
@ MarkSowul: Hmm ... parece que vale a pena relatar como um bug então. Não há razão para que seja tão ruim assim.
Jon Skeet
34

Eu acho que isso vai ajudar

Assert.IsTrue(expected.SequenceEqual(actual));
Shyju
fonte
4
Esse também foi o meu retorno, mas espero que o CollectionAssert forneça mensagens de falha mais úteis.
Jon Skeet
4
Infelizmente, isso realmente não: "CollectionAssert.AreEqual falhou (elemento no índice 0 não coincidem.)" (Quais são os elementos?)
namey
17

Se você deseja verificar se cada um contém a mesma coleção de valores, use:

CollectionAssert.AreEquivalent(expected, actual);

Editar:

"Duas coleções são equivalentes se tiverem os mesmos elementos na mesma quantidade, mas em qualquer ordem. Os elementos são iguais se seus valores forem iguais, não se eles se referirem ao mesmo objeto." - https://msdn.microsoft.com/en-us/library/ms243779.aspx

topham101
fonte
14

Tentei as outras respostas neste segmento, e elas não funcionaram para mim e eu estava comparando coleções de objetos que tinham os mesmos valores armazenados em suas propriedades, mas os objetos eram diferentes.

Chamada de método:

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

Método para comparações:

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);
        }
    }
Declan
fonte
3
Além disso, você também pode substituir o Equalsmétodo e CollectionAssertisso funcionará.
21814 Ray Cheng
6

esse teste compara uma entrada de data, verifica se é um ano bissexto; nesse caso, gera 20 anos bissextos a partir da data inserida; caso contrário, gera os próximos 20 anos bissextos, myTest.Testing refere-se à instância myTest que, por sua vez, chama os valores de uma lista chamada Teste contendo os valores calculados necessários. parte de um exercício que eu tive que fazer.

[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);
        }
gettingThereSlowly
fonte
0
List<AdminUser> adminDetailsExpected = new List<AdminUser>()
{
new AdminUser  {firstName = "test1" , lastName = "test1" , userId = 
"001test1"  },
new AdminUser {firstName = "test2" , lastName = "test2" , userId = 
"002test2"   }
};

//Aja

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

//Afirmar

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
karthik kasubha
fonte
0

Asserções fluentes fazem comparações profundas de matrizes actualArray.Should().BeEquivalentTo(expectedArray)

Ram Pratap
fonte