NUnit,ExpectedException和yield return的奇怪行为

Car*_*ist 9 c# testing nunit yield expected-exception

我在测试中有一个奇怪的行为,我想测试当作为参数传入null时抛出异常.当我运行测试时,我从NUnit获得:

    System.ArgumentNullException was expected
    -- Exception doesn't have a stack trace -- 
Run Code Online (Sandbox Code Playgroud)

我的测试:

[Test]
[ExpectedException(typeof(ArgumentNullException))]
public void Should_not_retrieve_any_fields_when_file_is_null()
{
    _creator.CreateFields(null);
}
Run Code Online (Sandbox Code Playgroud)

我的实施:

public IEnumerable<ImportField> CreateFields(HttpPostedFileBase file)
{
    if (file == null) throw new ArgumentNullException("file");

    using (var reader = new StreamReader(file.InputStream))
    {
        var firstLine = reader.ReadLine();
        var columns = firstLine.Split(new[] { ',' });

        for (var i = 0; i < columns.Length; i++)
        {
            yield return new ImportField(columns[i], i);
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

这种行为是否有合理的解释,我应该以不同的方式实现我的实现吗?

and*_*akk 10

您获得此行为的原因是yield关键字.使用yield时,编译器将为该方法生成一个类,其中包含yield.调用该方法时,无条件地将控制权返回给调用者.您的方法中的任何内容都不会在需要之前执行.

如果将using语句提取到单独的方法中并返回结果,则测试将通过.或者,您可以将结果存储到测试中的变量中,例如,在其上调用"ToList()".

    public IEnumerable<ImportField> CreateFields(HttpPostedFileBase file)
    {
        if (file == null) throw new ArgumentNullException("file");

        return ExtractFromFile(file);
    }

    private IEnumerable<ImportField> ExtractFromFile(HttpPostedFileBase file)
    {
        using (var reader = new StreamReader(file.InputStream))
        {
            var firstLine = reader.ReadLine();
            var columns = firstLine.Split(new[] { ',' });

            for (var i = 0; i < columns.Length; i++)
            {
                yield return new ImportField(columns[i], i);
            }
        }
    }
Run Code Online (Sandbox Code Playgroud)