1

I have this class with its constructor

 public class BankAccount
    {
    public int Id { get; private set; }
    public int BankAccountNo { get; private set; }
    public decimal Balance { get; private set; }

    public BankAccount(int BankAccountNo, decimal Balance)
    {
        this.BankAccountNo = BankAccountNo;

        if(Balance <= 0)
        {
            throw new ArgumentException("Create bank account failed. Balance should be more than zero.");
        }

        this.Balance = Balance;
    }
}

I have created xunit unit test for check object equality

public class BankAccountTest { private BankAccount _bankAccount;

    public BankAccountTest()
    {
        _bankAccount = new BankAccount();
    }

    [Theory, MemberData(nameof(BankAccountConstructorShouldPass_Data))]
    public void BankAccountConstructorShouldPass(BankAccount account, BankAccount accountExpected)
    {
        // Act
        _bankAccount = new BankAccount(account.BankAccountNo, account.Balance);

        // Assert
        Assert.Equal<BankAccount>(accountExpected,_bankAccount);
    }

    public static TheoryData<BankAccount, BankAccount> BankAccountConstructorShouldPass_Data()
    {
        return new TheoryData<BankAccount, BankAccount>
        {
            {
                new BankAccount(123, 250.00M),        
                new BankAccount(123, 250.00M)
            },
            {
                new BankAccount(321, 150.50M),       
                new BankAccount(321, 150.50M)
            }
        };
    }
}

When I run the test, it failed with error

Assert.Equal() Failure
Expected: BankAccount { Balance = 250.00, BankAccountNo = 123, Id = 0 }
Actual:   BankAccount { Balance = 250.00, BankAccountNo = 123, Id = 0 }

I tried with Assert.True(accountExpected.Equals(_bankAccount)); but no success still.

Steve
  • 2,963
  • 15
  • 61
  • 133
  • 2
    Does this answer your question? [Best way to compare two complex objects](https://stackoverflow.com/questions/10454519/best-way-to-compare-two-complex-objects). You can always serialize them both and check the resulting strings – Jawad Jun 16 '20 at 01:43
  • 1
    Google for `xunit compare two objects`. https://buildplease.com/pages/testing-deep-equalilty/ – mjwills Jun 16 '20 at 02:04
  • Thanks. Managed to solve it using FluentAssertions. `accountExpected.Should().BeEquivalentTo(_bankAccount);`. But, I can't figure out yet how to solve it without FluentAssertions. – Steve Jun 16 '20 at 02:06

2 Answers2

1

The assert fails because you are comparing your object reference location in memory. Instead you should assert on the properties inside the object.

https://medium.com/@pjbgf/asserting-equality-in-your-c-unit-tests-837b423024bf#:~:text=Equal(expected.Name%2C%20actual,object%20within%20the%20memory%20heap.

Jeff
  • 810
  • 8
  • 18
1

You are trying to compare two objects that are not Equatable! In C# in order to be able to compare two objects, they need to be Equatable, in other words the underlying class has to implement IEquatable, if you don't implement IEquatable<T> for a reference type, an equality check would simply check the object references! (note that this behavior is different for value types!)

So what you need to do is either of the follwoing -

  1. Implement IEquatable for your BackAccount class by following How to define value equality for a type
  2. Alternatively you can compare individual fields one by one:
Assert.Equal(bankAccount1.Balance, bankAccount2.Balance)

Also here is a good blog post about equality assertin:

Arin Ghazarian
  • 5,105
  • 3
  • 23
  • 21