我在理解这里的问题时遇到了一些麻烦.我有一些代码使用LINQ从数据库中提取记录,并将它们放入一个被转换为接口的对象中.看起来有点像这样:
public IEnumerable<ISomeObject> query()
{
return from a in dc.SomeTable
select new SomeObject
{
//Assign various members here
} as ISomeObject;
}
Run Code Online (Sandbox Code Playgroud)
当我测试它时,我将返回的IEnumerable放入一个名为results的变量中并运行以下行:
Assert.AreEqual(EXPECTED_COUNT, results.Count());
Run Code Online (Sandbox Code Playgroud)
运行它时,我得到一个System.Security.VerificationException:"操作可能会破坏运行时的稳定性."
我在这里找到了解决方案,这是:
var results = from a in dc.SomeTable
select new SomeObject
{
//Assign various members here
} as ISomeTable;
return results.OfType<ISomeObject>();
Run Code Online (Sandbox Code Playgroud)
这有效,但我无法理解这里发生的事情.为什么我首先得到异常,上面的代码行是如何解决的?MSDN文档似乎表明这是类型安全的问题,但我没有看到以前的代码类型不安全的地方.
更新 我发现的更多信息.如果我返回类型IQueryable,第一个示例有效.这揭示了一点点光什么是走错了,但我仍然感到困惑的原因.为什么编译器不强迫我将IEnumerable转换为IQueryable?
每当我运行附带调试器的以下任一单元测试时,我都会VerificationException在此时获得一个内部FluentValidation代码(如果需要,将在稍后发布整个堆栈跟踪):
at FluentValidation.Resources.LocalizedStringSource.CreateFromExpression(Expression`1 expression, IResourceAccessorBuilder resourceProviderSelectionStrategy)
in ...\FluentValidation\Resources\LocalizedStringSource.cs:line 66
Run Code Online (Sandbox Code Playgroud)
测试是:
using FluentValidation;
using Microsoft.VisualStudio.TestTools.UnitTesting;
[TestClass]
public class UnitTest1
{
[TestMethod]
public void TestMethod1()
{
var c = new MyClass();
var v = new MyValidator();
v.Validate(c);
}
[TestMethod]
public void TestMethod2()
{
Exception ex = null;
var done = new ManualResetEvent(false);
ThreadPool.QueueUserWorkItem(
o =>
{
try
{
TestMethod1();
}
catch (Exception e)
{
ex = e;
}
finally
{
done.Set();
}
});
done.WaitOne(); …Run Code Online (Sandbox Code Playgroud)