对象的新实例实际上是重用现有对象

时间:2016-06-08 14:53:36

标签: c# unit-testing object constructor

我在VS2015中设置了自定义类的单元测试。我注意到在同一个类上运行两个测试方法时看起来很奇怪。这是问题的简化:

public MyClass
{
    private List<string> _MyList = new List<string>();
    public void AddItem(string s)
    {
        _MyList.Add(s);
    }
    public List<string> GetList()
    {
        return _MyList;
    }
}

[TestMethod]
public void AddSingleItem()
{
    MyClass instance = new MyClass();
    instance.AddItem("string 1");
    Assert.AreEqual(1, instance.GetList().Count);
}

[TestMethod]
public void AddMultipleItems()
{
    MyClass instance = new MyClass();
    instance.AddItem("string 1");
    instance.AddItem("string 2");
    Assert.AreEqual(2, instance.GetList().Count);
}

问题是第一个测试通过正常,第二个测试在单独运行时正常运行,但如果一起运行,第二个测试将失败,说断言预期和实际不同,就好像方法是添加字符串一样到同一个对象(尽管已经创建了一个新实例)。

我在类中添加了一个构造函数,确保_MyList在实例化时被清除,这解决了问题,但我想知道这是否是预期的,为什么?是否必须使您的默认构造函数清除所有属性,这是标准做法吗? new MyClass()实际上并没有真正生成一个全新的实例,这似乎很奇怪。

作为参考,这里是我提到的构造函数:

public MyClass()
{
    _MyList.Clear();
}

1 个答案:

答案 0 :(得分:2)

没有理由使用您发布的代码来描述您所描述的行为。我猜你在简化问题时改变了一些关键的东西。很可能是你的私人领域:

private List<string> _MyList = new List<string>();

可能是静态的:

private static List<string> _MyList = new List<string>();

这会导致您的类的每个实例重用相同的实例。添加一个重置此值的构造函数会给出修复问题的外观,但是这会导致更多问题,因为您创建的第一个实例每次创建新实例时都会重置其列表。您可能会开始看到难以追踪的怪异竞争条件,等等。

如果是这种情况,确保该字段不是static应该解决问题。