如何对返回 Func 的 C# 函数进行单元测试?
我有一个类,其中包含一个返回 Result 对象的方法,该对象包含 Func 类型的属性。
class Result {
public Func<Result> NextAction { get; set; }
}
如何编写有关此 Func 内容的单元测试断言?以下显然不起作用,因为编译器为 lambda 生成两种不同的方法:
// Arrange
ListController controller = new ListController(domain);
// Act
Result actual = controller.DefaultAction();
// Assert
Func<Result> expected = () => new ProductsController(domain).ListAction();
Assert.That(actual.NextAction, Is.EqualTo(expected));
我猜我可以通过使用表达式树来实现此目的,但是......有没有办法避免这样做?我正在使用 NUnit 2.5。
编辑: Result 对象中没有其他标识字段。它旨在成为一种基于当前对象/方法中做出的决策来调用下一个对象/方法的方法。
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(5)
为什么不调用
Func
并比较返回值?编辑:我看到 Result 类没有任何标识。我猜想 Result 类中还有一些其他字段定义了 Result 的标识,可用于确定两个结果是否相等。
Why not invoke the
Func
and compare the returned values?EDIT: I see that the Result class does not have any identity. I guess you have some other fields in the Result class that define the identity of the Result and can be used to determine if two results are equal.
我不知道有一种简单的方法来查看 lambda 内部(除了如您所说的使用表达式树之外),但如果为委托分配了 方法组 代替。
如果您使用 lambda,上面的示例将不起作用,因为它们被编译为不同的方法。
I'm not aware of an easy way to look inside a lambda (other than using expression trees as you said) but it is possible to compare delegates if they're assigned a method group instead.
The above example does not work if you use lambdas since they are compiled to different methods.
如果您
Func
始终返回相同的结果,您可以测试函数返回哪个对象。If you
Func<Result>
always return the same result you can test which object is returned by the function.看来对
Func
的内容进行单元测试超出了单元测试的正常范围。Func
表示已编译的代码,因此在不解析 MSIL 的情况下无法进一步检查。因此,在这种情况下,有必要依靠委托和实例化类型(如 Nathan Baulch 所建议的),或者改用表达式树。我的表达式树等效如下:
单元测试如下:
请注意,此测试存在一些固有的脆弱性,因为它暗示了表达式的结构及其行为。
Well it appears that unit testing the contents of a
Func
goes beyond the normal range of unit testing. AFunc
represents compiled code, and therefore can not be further inspected without resorting to parsing MSIL. In this situation, it is therefore necessary to fall back on delegates and instantiated types (as suggested by Nathan Baulch), or to use expression trees instead.My expression tree equivalent below:
with the unit testing as follows:
Note that there is some inherent fragility to this test as it implies the structure of the expression, as well as its behaviour.
如果我正确理解了这个问题,NextAction 可能有也可能没有不同的 lambda 实现,这就是需要测试的地方。
在下面的示例中,我比较了 IL 字节的方法。使用反射,从数组中的主体获取方法信息和 IL 字节。如果字节数组匹配,则 lambda 相同。
有很多情况这无法处理,但如果只是比较两个应该完全相同的 lambda 的问题,那么这将起作用。抱歉,它在 MSTest 中:)
If I understand the issue properly the NextAction may or may not have a different lambda implementation, which is what needs testing.
In the example below I compare the methods IL bytes. Using reflection, get the method info and IL bytes from the body in an array. If the byte arrays match, the lambda's are the same.
There are lots of situations that this wont handle, but if it's just question of comparing two lambda's that should be exactly the same, this will work. Sorry it's in MSTest :)