[英]Linq-to-SQL: Ignore null parameters from WHERE clause
The query below should return records that either have a matching Id supplied in ownerGroupIds or that match ownerUserId . 下面的查询应该返回在ownerGroupIds中提供匹配ID或匹配ownerUserId的记录 。 However is ownerUserId is null, I want this part of the query to be ignored.
但是ownerUserId为null,我希望忽略查询的这一部分。
public static int NumberUnderReview(int? ownerUserId, List<int> ownerGroupIds)
{
return ( from c in db.Contacts
where
c.Active == true
&&
c.LastReviewedOn <= DateTime.Now.AddDays(-365)
&&
( // Owned by user
!ownerUserId.HasValue ||
c.OwnerUserId.Value == ownerUserId.Value
)
&&
( // Owned by group
ownerGroupIds.Count == 0 ||
ownerGroupIds.Contains( c.OwnerGroupId.Value )
)
select c ).Count();
}
However when a null is passed in for ownerUserId then I get the following error: Nullable object must have a value.
但是,当为ownerUserId传入null时,我收到以下错误:
Nullable object must have a value.
I get a tingling I may have to use a lambda expression in this instance? 在这种情况下,我可能不得不使用lambda表达式?
your issue is that your are not passing in a nullable int, you are passing in a null. 你的问题是你没有传入一个可以为空的int,你传递的是null。
try this: 试试这个:
Print(null);
private void Print(int? num)
{
Console.WriteLine(num.Value);
}
and you get the same error. 你得到同样的错误。
It should work if you do this: 它应该工作如果你这样做:
var q = ( from c in db.Contacts
where
c.Active == true
&&
c.LastReviewedOn <= DateTime.Now.AddDays(-365)
&&
( // Owned by group
ownerGroupIds.Count == 0 ||
ownerGroupIds.Contains( c.OwnerGroupId.Value )
)
select c );
if(ownerUserId != null && ownerUserId.HasValue)
q = q.Where(p => p.OwnerUserId.Value == ownerUserId.Value);
return q.Count();
Have you some contacts with OwnerUserId null? 你和OwnerUserId有一些联系吗? If yes,
c.OwnerUserId
could be null and not having any value in c.OwnerUserId.Value
如果是,则
c.OwnerUserId
可以为null,并且在c.OwnerUserId.Value
没有任何值
What about conditionally adding the where clause to the expression tree? 有条件地将where子句添加到表达式树中怎么样?
public static int NumberUnderReview(int? ownerUserId, List<int> ownerGroupIds)
{
var x = ( from c in db.Contacts
where
c.Active == true
&&
c.LastReviewedOn <= DateTime.Now.AddDays(-365)
&&
( // Owned by group
ownerGroupIds.Count == 0 ||
ownerGroupIds.Contains( c.OwnerGroupId.Value )
)
select c );
if (ownerUserId.HasValue) {
x = from a in x
where c.OwnerUserId.Value == ownerUserId.Value
}
return x.Count();
}
PROBLEM: "&&" and "||" 问题:“&&”和“||” is converted to a method like "AndCondition(a, b)", so "!a.HasValue || a.Value == b" becomes "OrCondition(!a.HasValue, a.Value == b);"
被转换为像“AndCondition(a,b)”这样的方法,所以“!a.HasValue || a.Value == b”变为“OrCondition(!a.HasValue,a.Value == b);” The reason for this is probably to get a generic solution to work for both code and SQL statements.
这样做的原因可能是获得适用于代码和SQL语句的通用解决方案。 So instead, use the "?:" notation.
因此,请使用“?:”表示法。
For more, see my blog post: http://peetbrits.wordpress.com/2008/10/18/linq-breaking-your-logic/ 有关更多信息,请参阅我的博客文章: http : //peetbrits.wordpress.com/2008/10/18/linq-breaking-your-logic/
// New revised code.
public static int NumberUnderReview(int? ownerUserId, List<int> ownerGroupIds)
{
return ( from c in db.Contacts
where
c.Active == true
&&
c.LastReviewedOn <= DateTime.Now.AddDays(-365)
&&
( // Owned by user
// !ownerUserId.HasValue ||
// c.OwnerUserId.Value == ownerUserId.Value
ownerUserId.HasValue ? c.OwnerUserId.Value == ownerUserId.Value : true
)
&&
( // Owned by group
// ownerGroupIds.Count == 0 ||
// ownerGroupIds.Contains( c.OwnerGroupId.Value )
ownerGroupIds.Count != 0 ? ownerGroupIds.Contains( c.OwnerGroupId.Value ) : true
)
select c ).Count();
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.