C# 为什么';提交。其中(s=>;(false&;s.Status==Convert.ToInt16(";)&x27;引发格式化异常?

C# 为什么';提交。其中(s=>;(false&;s.Status==Convert.ToInt16(";)&x27;引发格式化异常?,c#,linq,C#,Linq,我认为该查询非常简单,但它引发了FormatException(“输入字符串的格式不正确”): Submissions.Where(s => (false && s.Status == Convert.ToInt16(""))) (当然,在我的代码中,另一个计算结果为“false”的表达式位于“&&&”之前) 那么为什么要计算“&&”之后的部分,因为第一部分始终为false,并且整个表达式的计算结果永远不能为true 这种情况特别奇怪,因为只有Convert.ToInt1

我认为该查询非常简单,但它引发了FormatException(“输入字符串的格式不正确”):

Submissions.Where(s => (false && s.Status == Convert.ToInt16("")))
(当然,在我的代码中,另一个计算结果为“false”的表达式位于“&&&”之前)

那么为什么要计算“&&”之后的部分,因为第一部分始终为false,并且整个表达式的计算结果永远不能为
true

这种情况特别奇怪,因为只有
Convert.ToInt16(“”
部分似乎引发了一个异常——我的原始查询的其他部分或多或少具有相同的结构,如

Submissions.Where(s => (false && s.SubmissionDate <= DateTime.Now))

Submissions.Where(s=>(false&&s.SubmissionDate如果
Submissions
是一个
IQueryable
,那么这不是一个常规的C委托,而是一个表达式树。一些代码(LINQ提供程序)必须将这棵树拆开并理解它-因此,如果表达式中有奇怪的地方,则需要奇怪的输出。

根据您在评论中对我的问题的回答,因为它是Linq to Sql,所以它实际上不是一个委托。我尝试使用Linq to Objects重新创建它,并且确信没有任何问题。VS实际指出在“检测到不可访问的代码”处。因为在您的示例中,它实际上是Linq to Sql,所以它正在构建一个表达式树,在这种情况下,它必须解码所有内容,并且所有赌注都被取消。

建议:使用静态Int16保存Convert.ToInt16(“”)的结果,然后引用谓词中的静态


更好的是,您知道Convert.ToInt16(“”)的结果是什么吗是吗?是吗?然后改为使用它。例如,如果它是0,那么说s.Status==0。你甚至可以将它设为常量。

正如其他人所指出的,LINQ to SQL代码在作为SQL代码对数据库运行之前会被分解到表达式树中。因为SQL不一定遵循与C#相同的短路布尔规则,表达式代码的右侧可能会被解析,以便可以构造SQL

发件人:

C#指定短路语义 基于操作数的词法顺序 逻辑运算符&&和| |.SQL on 另一方面是针对 基于集合的查询,因此 为用户提供更多的自由 优化器来决定 执行


至于为什么这段代码会出现异常,
Convert.ToInt16(“”)
将始终准确地抛出该异常,因为无法将空字符串转换为整数。您的另一个示例不会尝试无效转换,因此它运行时不会出现问题。

这是Linq到对象还是Linq到Sql?您能整理一下这个问题的标题吗?这是一个好问题,但标题实际上并不正确需要代码。我添加了一个计算正确的类似查询的示例。为什么第一个示例明显“奇怪”,而第二个则不奇怪?@hwschuur-请参阅我的答案,以解释为什么一个有效,另一个无效。简单地说,它需要为表达式创建TSQL。据猜测,在尝试计算Con时,它正在中断将vert.ToInt16(“”)转换为常量(进入TSQL字符串)或参数值。