[英]LINQ to SQL query succeeds or fails based on using foreign key versus using a built in navigation property
I have a query against a SQL server database that throws an Error converting data type nvarchar to numeric.
我有一个针对SQL Server数据库的查询,该查询引发
Error converting data type nvarchar to numeric.
exception. 例外。 I was trying to use
Convert.ToDecimal
on a varchar field, however I'll eyeballed the data as best I could and couldn't find an invalid value. 我试图在varchar字段上使用
Convert.ToDecimal
,但是我将尽我所能地盯着数据,并且也找不到无效的值。
The query is filtering the table by a 'Group' by using the foreign key of p.pgKey=#
. 该查询正在使用
p.pgKey=#
的外键按“组”过滤表。 However, if I use the navigation property and filter by the navigation property instead, p.Group.gName='ABC'
the query works. 但是,如果我使用导航属性并改为按导航属性过滤,则
p.Group.gName='ABC'
可以运行查询。
Here are the queries (note, originally, I didn't know if error was happening in Where
translation or the Select
processing, so that is why query looks weird, but as you can guess, when it works, it should just return a single distinct row of true
): 这是查询(请注意,最初,我不知道在
Where
翻译或Select
处理中是否发生错误,因此这就是查询看起来很奇怪的原因,但是您可以猜测,当它起作用时,它应该只返回一个true
不同行):
Profiles
.Where(p =>
p.pgKey == 237
&& !p.pPlanProfile.Value
&& Convert.ToDecimal(p.pSearch08 ?? "0") > 0
).Select(p =>
Convert.ToDecimal(p.pSearch08 ?? "0") > 0
)
.Distinct()
.Dump();
The above query fails, while this query succeeds: 以上查询失败,而该查询成功:
Profiles
.Where(p =>
p.Groups.gName == "ABC"
&& !p.pPlanProfile.Value
&& Convert.ToDecimal(p.pSearch08 ?? "0") > 0
).Select(p =>
Convert.ToDecimal(p.pSearch08 ?? "0") > 0
)
.Distinct()
.Dump();
Below is a full LINQPad screen dump showing: 下面是完整的LINQPad屏幕转储,显示:
gKey
for ABC is 237. gKey
为237。 pgKey
or Group.gName
. pgKey
或Group.gName
时, pgKey
统计Profile记录的计数是相同的。 Group.gName
processing. Group.gName
处理时查询正常工作。 pgKey
processing. pgKey
处理时显示查询失败。 Obviously I've used the Group.gName
method to fix my problem, but I stumbled on that solution by accident. 显然,我已经使用
Group.gName
方法解决了我的问题,但是偶然发现了该解决方案。 Anyone know why LINQ to SQL would behave this way? 有人知道为什么LINQ to SQL会这样吗?
Note : I get the same behavior using the generated DataContext from LINQPad or if I run against a compiled .dbml DataContext. 注意 :使用LINQPad生成的DataContext或针对编译的.dbml DataContext运行时,我会得到相同的行为。
The two queries will be generating different TSQL and hence the query plan will be different. 这两个查询将生成不同的TSQL,因此查询计划将不同。
I would suspect that the former query is attempting to convert some values of pSearch08 to decimal before it rejects them based on the other selection criteria, whereas the latter query is performing the other selection criteria first and hence is attempting to convert a smaller number of pSearch08 values to decimal and hence does not attempt to convert the invalid value. 我怀疑前一个查询试图将pSearch08的某些值转换为十进制, 然后才根据其他选择条件拒绝它们,而后一个查询首先执行其他选择条件,因此尝试转换较少的pSearch08值转换为十进制,因此不会尝试转换无效值。
If this is the case, then it could be dangerous to assume that the second query will always work and it would be best to fix the invalid data. 如果是这种情况,那么假设第二个查询将始终有效,则最好进行修复,以修复无效数据。
Rather than eyeballing the data you can try 不必盯着数据,您可以尝试
SELECT * from Profile where ISNUMERIC(pSearch08) = 0
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.