.net 如何模拟IEnumerable<;T>;这样我就可以测试接收它的方法
我有一个我想测试的方法,它需要一个.net 如何模拟IEnumerable<;T>;这样我就可以测试接收它的方法,.net,unit-testing,mocking,moq,.net,Unit Testing,Mocking,Moq,我有一个我想测试的方法,它需要一个IEnumerable作为参数 我目前正在模拟IEnumerable的内容,如下所示(使用Moq): var mockParent=new Mock(); var mockChild=new Mock(); 如何将这些模拟对象放在IEnumerable中,以便将它们作为参数传递给要测试的方法 我正在测试的方法希望收到一个IEnumerable我只需要使用集合初始化器语法创建一个数组。i、 e var mockParent = new Mock<ICsvT
IEnumerable
作为参数
我目前正在模拟IEnumerable
的内容,如下所示(使用Moq):
var mockParent=new Mock();
var mockChild=new Mock();
如何将这些模拟对象放在IEnumerable
中,以便将它们作为参数传递给要测试的方法
我正在测试的方法希望收到一个
IEnumerable
我只需要使用集合初始化器语法创建一个数组。i、 e
var mockParent = new Mock<ICsvTreeGridExportable>();
var mockChild = new Mock<ICsvTreeGridExportable>();
TestMethod(new[] { mockParent.Object, mockChild.Object });
您可以创建一个数组。(数组实现
IEnumerable
接口。)
如果您想要一个不能回溯到数组等的“纯”IEnumerable
,则可以使用助手方法创建它:
var mockEnumerable = CreateEnumerable(mockParent.Object, mockChild.Object);
// ...
public static IEnumerable<T> CreateEnumerable<T>(params T[] items)
{
foreach (T item in items)
{
yield return item;
}
}
var mockEnumerable=CreateEnumerable(mockParent.Object,mockChild.Object);
// ...
公共静态IEnumerable CreateEnumerable(参数T[]项)
{
foreach(项目中的T项目)
{
收益回报项目;
}
}
(正如Jamie在评论中提到的,您需要使用模拟对象,而不是
Mock
对象。例如,mockParent.Object
,mockChild.Object
等,而不仅仅是mockParent
或mockChild
)您可以这样做:创建一个虚拟函数
private IEnumerable<ICsvTreeGridExportable> Dummy()
{
yield return new ICsvTreeGridExportable();
}
希望对您有所帮助List myList=newlist();
List<ICsvTreeGridExportable> myList = new List<ICsvTreeGridExportable>();
myList.Add(mockParent);
myList.Add(mockChild);
return myList;
myList.Add(mockParent);
myList.Add(mockChild);
返回myList;
这里有一个替代塞巴斯蒂安答案的选项,它允许您指定您想要的任何类型的假人数量:
private IEnumerable<T> GetDummies<T>(int numDummies) where T : new() {
for (int i = 0; i < numDummies; i++) yield return new T();
yield break;
}
private IEnumerable GetDummies(int numDummies),其中T:new(){
对于(int i=0;i
或者(如果希望使用,则可以使用没有空构造函数的类型):
private IEnumerable GetDummies(函数生成器,int numDummies){
对于(inti=0;i
yap。。。比我的解决方案简单得多(+1)Noldorin,如果您可以将答案更改为mockParent.Object和mockChild.Object,那么我可以将其标记为正确答案。下面的答案也非常有帮助。遗憾的是,我不能将两者都标记为已接受:)我想他想要一个由多个元素组成的IEnumerable
。是的,有了收益率回报,你可以随心所欲地回报。。。我错过了…@塞巴斯蒂安:真的。但是,如果您想要“惰性初始化”,即仅在需要时创建对象,则此方法可能非常有用。此Dummy()
函数是否将提供一组永无止境的对象?不。。。实际上,在给定的示例中,它只返回一个object。当我尝试将mockEnumerable传递给该方法时,我得到以下错误:Argument.Type'Moq.Mock[]不可分配给参数类型IEnumerable。我需要做什么来确保我的模拟对象是正确的类型呢?CreateEnumerable
方法正是我最初考虑的方法,但它与数组相比没有任何优势。不管怎样,编译器都会生成一个伪类。然而,如果你想要懒散的初始化(参见sebastian的答案),它可能是有用的。这仍然给了我同样的问题。当我使用IEnumerable x=CreateEnumerable(mockParent,mockChild)时;我仍然被告知“无法转换源类型”。一个是IEnum型。。。另一种类型是IEnum…@Noldorin:使用“纯”可枚举性很方便进行测试。我见过一些方法声称采用IEnumerable
,但在内部盲目地转换为IList
或类似的方法。如果您使用数组或列表测试这些方法,那么它们将通过测试,使用“pure”IEnumerable
测试,您将发现这些错误!好的,在你们的帮助下我已经弄明白了。我需要做的是将mocked objects对象添加到数组中,以便在我的方法中使用。var mockEnumerable=new[]{mockParent.Object,mockChild.Object};--所以我使用mockParent.Object而不仅仅是mockParent。现在,这将强制转换为我的方法要接受的正确类型。:)
private IEnumerable<ICsvTreeGridExportable> Dummy()
{
yield return new ICsvTreeGridExportable();
}
private void TestFunction()
{
ThisIsTheOneThatNeedsIenumerable(Dummy());
}
List<ICsvTreeGridExportable> myList = new List<ICsvTreeGridExportable>();
myList.Add(mockParent);
myList.Add(mockChild);
return myList;
private IEnumerable<T> GetDummies<T>(int numDummies) where T : new() {
for (int i = 0; i < numDummies; i++) yield return new T();
yield break;
}
private IEnumerable<T> GetDummies<T>(Func<T> generator, int numDummies) {
for (int i = 0; i < numDummies; i++) yield return generator.Invoke();
yield break;
}