默认情况下,.Net中的所有方法都被视为最终方法,除非使用了虚拟修饰符。Java是另一种方式。所有的方法都是虚拟的,并且可以被覆盖。当涉及到使用Moq、RhinoMock等框架进行单元测试时,我们可以创建一个模拟或存根。如果我们要创建一个mock,我们需要一个接口。这迫使我们在任何地方都使用接口,如果不是仅仅为了能够测试我们的代码。
另一方面,我们可以创建存根,但是我们要存根的方法需要是虚拟的,这样框架才能覆盖它们。
有其他使用面向方面编程的模拟框架,比如TypeMock,但我不确定我能不能在这样的框架上花钱,因为有这么好的开源和免费的框架。
我知道非虚拟方法和接口方法都稍微慢一些。但这应该不会真正影响当今硬件上的应用程序。
所以我的问题是:几乎所有的东西都应该是一个接口,即使它并不是真正封装了某种行为?或者,我们是否应该根据需要将方法虚拟起来,以帮助我们的测试。对我来说,这两个都有点老生常谈,没有必要。
你的想法是什么?
发布于 2011-03-04 16:14:24
就我个人而言,我发现对依赖项使用接口无论如何都会改进设计。它清楚地表明您所依赖的是什么,而不仅仅是实现类恰好公开的任何公共和内部方法。
请注意,这并不意味着每个类都需要一个接口……只是那些您希望作为依赖项的对象。例如,我不会为大多数是“简单数据”或异常的类型创建接口。但是,如果一个类在某些方面充当“服务”,那么接口就是合适的。如果有一种更简单的方式来表达这个接口,而不是有一个单独的文件,那就太好了,但从概念上讲,我认为它是干净的。
(我意识到,这个观点让我有点守旧,但它至少帮助我理解了我的设计:)
发布于 2011-03-04 16:21:52
我倾向于将我的解决方案划分为具有明确定义的职责领域的组件,例如一组类和其他类型一起工作来解决某些特定问题。构成此类组件的公共外观的类通常从拥有接口中获益良多,因为它允许我轻松地替换或存根它们,以便进行测试和一般维护。您是否只是为了单元测试的目的而为内部使用的类添加接口,这通常由内部复杂性以及组件本身是否使用其他需要清除的组件来决定。
考虑到Visual Studio甚至内置了必要的重构选项(右键单击、重构->提取接口),为类创建接口真的非常简单。因此,创建接口的编码工作在某种程度上是微不足道的(假设设计是由类的外观驱动的)。
尽管随着时间的推移,维护这些接口需要付出一些努力,但我发现自己经常使用它们。它减少了应用程序接口的公共表面,这使得维护变得更容易,如果您有像R#这样的工具,那么几乎不需要额外的工作。
值得一提的是,TypeMock和Moles ( Pex的伙伴)都与分析API挂钩。因此,它在某种程度上不同于AOP,尽管它们提供类似AOP的功能。当您需要拦截静态方法或常规字段访问时,这些方法非常有用,因为这些访问不能使用接口进行建模。
发布于 2011-03-04 16:27:09
我通常发现,我通常针对具体类型之间的松散耦合、控制反转和依赖注入的接口进行编码,以帮助实现可测试性。
然而,就像你所说的,创建界面的时候可能会有一些噪音。在这些特定场景中,您需要权衡是否
<>G29
(我会同时考虑3和4)
如果您发现您确实需要能够模拟/存根类型,那么对于大多数框架,您将需要提供一些机制来实现这一点,而虚拟成员和接口是两个显而易见的选择。
不需要接口或虚拟成员的模拟和存根框架是Typemock、Moles和我相信JustMock。前两个使用profiling API (我相信JustMock也是),它本质上将方法调用重定向到您定义的其他地方。关于能够做到这一点是否是一件好事还存在一些争论,因为这可能意味着你必须少考虑设计,但确实有一些时候它可以真正起到帮助作用(DateTime.Now就是一个典型的例子)。
https://stackoverflow.com/questions/5191208
复制相似问题