6

我正在使用 Visual Studio 进行测试驱动开发的第一步。我对如何使用 VS 2010 实现泛型类有一些疑问。

首先,假设我想实现我自己的 ArrayList 版本。我首先创建以下测试(在本例中我使用的是 MSTest):

[TestMethod]
public void Add_10_Items_Remove_10_Items_Check_Size_Is_Zero() {
    var myArrayList = new MyArrayList<int>();

    for (int i = 0; i < 10; ++i) {
        myArrayList.Add(i);
    }

    for (int i = 0; i < 10; ++i) {
        myArrayList.RemoveAt(0); //should this mean RemoveAt(int) or RemoveAt(T)?
                                 //VS doesn't know. Any work arounds?
    }

    int expected = 0;
    int actual = myArrayList.Size;
    Assert.AreEqual(expected, actual);
}

我正在使用 VS 2010 的能力打

Ctrl + 。

并让它在旅途中实现类/方法。

  1. 在实现泛型类时我遇到了一些麻烦。例如,当我定义一个.Add(10)方法时,VS 不知道我想要一个泛型方法(因为该类是泛型的)还是一个Add(int number)方法。有没有办法区分这个?
  2. 返回类型也会发生同样的情况。假设我正在实现一个MyStack堆栈,并且我想测试在我推送和元素并弹出它之后,堆栈是否仍然是空的。我们都知道 pop 应该返回一些东西,但通常,这个测试的代码不应该关心它。然后 Visual Studio 会认为 pop 是一个 void 方法,这实际上不是人们想要的。如何处理?对于每种方法,我是否应该首先进行“非常具体”的测试,例如很明显该方法应该返回一些东西,这样我就不会得到这种歧义?即使不使用结果,我应该有类似的东西int popValue = myStack.Pop()吗?
  3. 我应该如何对泛型类进行测试?仅使用一种通用类型进行测试?我一直在使用ints,因为它们易于使用,但我是否也应该使用不同类型的对象进行测试?你通常如何处理这个问题?
  4. 我看到有一个名为 TestDriven for .NET 的流行工具。随着 VS 2010 的发布,它是否仍然有用,或者它的许多功能现在是 VS 2010 的一部分,使它有点无用?
  5. 每当我在测试代码中定义一个新属性并要求 VS 为我生成该方法存根时,它都会生成一个 getter 和一个 setter。如果我有类似的事情int val = MyClass.MyProperty我想了解(至少现在)我只想定义一个吸气剂。

谢谢

4

2 回答 2

3

我看到有一个名为 TestDriven for .NET 的流行工具。随着 VS 2010 的发布,它是否仍然有用,或者它的许多功能现在是 VS 2010 的一部分,使它有点无用?

如果您使用许多不同的单元测试框架之一(nunitmbunitxunitcsunit等),它仍然很有用。

还有其他工具(如Visual Nunit)为运行单元测试提供了 Visual Studio 集成。

于 2010-05-16T17:54:05.767 回答
3

对于您的代码示例,您为什么要有一个方法RemoveAt(T obj)

你可以这样做RemoveAt(int index)Remove(T obj)而不是。查看 Microsoft 的 API(例如,对于 List<T>),了解它们如何为通用集合设置 Remove 方法。

现在为您的观点:

1:会Add(int number)做什么?如果我正确理解您的意图,Add(10)则只能解释为“在我的收藏结束时添加值 10”。如果您想在特定索引处添加一个值,您可以(并且可能应该)将该方法命名为 Insert: Insert(int index, T value)

2:当然,Visual Studio 最初会将该方法解释为 void,但您可以将其编辑为类似

public class MyStack<T>
{
    public T Pop() 
    {
    }
}

通过压制建立的存根Ctrl+.是一种方便,但不是福音。您不必总是为变量分配返回值。如果您在测试中不需要它,请不要这样做。如果您希望 VS 选择 void 以外的返回类型,您可以编写不同的单元测试(例如 Pop() 返回最后推送的值)。

3:我会使用我在代码中最常使用的类型进行测试。如果您正在编写公共 API,请使用尽可能多的类型进行测试。如果您使用的是 NUnit,请考虑使用该[TestCase]属性来帮助您避免编写一些重复的代码。

4:我仍然使用TestDriven,但我没有尝试过没有它,所以我无法真正做出有用的比较。

5:如果不需要,只需删除setter即可。一些插件框架(如ReSharper)支持更高级的代码生成,包括只读属性。

于 2010-05-16T18:00:26.653 回答