嘲笑一个对象,是否必须要么实现一个接口或标记虚拟?

还是class级也可以实现抽象类呢?

为了模拟一个types,它必须是一个接口(这也被称为纯虚拟 )或虚拟成员(抽象成员也是虚拟的)。

通过这个定义,你可以模拟一切虚拟的东西。

从本质上讲,dynamic模拟不会做任何你无法做到的事情

假设您正在针对如下这个接口进行编程:

public interface IMyInterface { string Foo(string s); } 

您可以手动创buildIMyInterface的特定于testing的实现,忽略input参数并始终返回相同的输出:

 public class MyClass : IMyInterface { public string Foo(string s) { return "Bar"; } } 

然而,如果你想testing消费者如何响应不同的返回值,那么这个过程变得非常快速,所以你可以用一个框架来dynamic地为你创build它们。

想象一下,dynamic模拟真的写代码类似于上面的MyClass实现(他们实际上没有写代码,他们dynamic地发出types,但是这是一个足够准确的类比)。

下面是你如何定义与Moq的MyClass相同的行为:

 var mock = new Mock<IMyInterface>(); mock.Setup(x => x.Foo(It.IsAny<string>())).Returns("Bar"); 

在这两种情况下,创build的类的构造将在创build对象时调用。 由于接口没有构造函数,因此它通常是默认的构造函数(MyClass和dynamic发射的类)。

你可以像这样的具体types做同样的事情:

 public class MyBase { public virtual string Ploeh() { return "Fnaah"; } } 

手动,你将能够从MyBase派生,并重写Ploeh方法,因为它是虚拟的:

 public class TestSpecificChild : MyBase { public override string Ploeh() { return "Ndøh"; } } 

dynamic模拟库可以做同样的事情,抽象方法也是如此。

但是,您不能编写覆盖非虚拟或内部成员的代码,也不能dynamic模拟。 他们只能做你能做的事情。

注意:以上描述对于大部分dynamic模拟都是正确的,除了TypeMock,这是不同的和…可怕的。

来自Stephen Walther的博客 :

您可以使用Moq从接口和现有类创build模拟。 对类有一些要求。 这个class不能被密封。 此外,被嘲笑的方法必须标记为虚拟。 你不能嘲笑静态方法(使用适配器模式来模拟静态方法)。