2010-02-21 5 views
5

null 참조 예외가 발생하지 않고 LINQ의 조건부 조건을 지정할 수있는 방법은 무엇입니까? 예를 들어, q가 된 IQueryable 경우 내가 좋아합니까 방법 : 여기 searchLINQ의 술어

Expression<Func<ProductEntity,bool>> predicate = p => !search.CategoryId.HasValue || (search.CategoryId.HasValue && search.CategoryId == p.CategoryId); 

var q2 = q.Where(predicate); 

것은 나 설정되지 않을 수 있습니다 search.CategoryId처럼 설정되지 않을 수 있습니다 가능한 검색 조건을 유지하는 목적이지만 경우 나는 그 조건에 의해 설정된 제품을 얻고 싶다.

이렇게하면 null 참조 예외가 발생합니다.

답변

7

가능한 null 값을 기본값으로 바꾸려면 null-coalescing operator??을 사용할 수 있습니다. 다음 세트는 search.Category가 존재하거나 단순히 "항상 참"인 표현식과 일치하도록 시도합니다. 이는 훌륭한 Linq 쿼리 공급자 (예 : LinqToSql)가 최적화합니다.

Expression<Func<ProductEntity,bool>> predicate = (p => (search.CategoryId ?? p.CategoryId) == p.CategoryId)); 

var q2 = q.Where(predicate); 

또 다른 가능성은 동적 PredicateBuilder를 사용하여 쿼리 조건을 구성하는 것입니다.

Expression<Func<ProductEntity,bool> predicate = p => !search.CategoryId.HasValue 
     || (search.CategoryId.HasValue && search.CategoryId == p.CategoryId) 
var q2 = q.Where(predicate); 

그래서 얼마나 많은 방법으로 우리가 null 문제를 가져올 수 있습니다

var predicate = PredicateBuilder.True<Order>(); 

if (search.OrderId)) 
{ 
    predicate = predicate.And(a => SqlMethods.Like(a.OrderID, search.OderID); 
} 
// ... 
var results = q.Where(predicate); 
3

이의 선을 해부 해보자 사용으로 그게 내가 비슷한 패턴 검색을 위해 그것을 할 방법입니까?

  • search (당신의 "캡처"변수) Nullable<T> (
  • 당신이 search.CategoryIdnull되는 경우를 처리 한 목록에서 null이 의미 null
  • p가 null이 될 수있을 수)
  • 어쩌면 p.CategoryId (목록의 레코드 범주)은 null (Nullable<T>)입니다. - howe 버전, 나는 이것이 NullReferenceException
  • q (목록/소스) 그래서 null

수 일으킬 것이 확실하지 않다 : 당신이 하나를 제거 한 5 개 옵션 중; 다른 4 번 봐? 입니다. 문제는 코드에 표시되지 않는 보이지 않는 항목으로 인해 발생할 수 있습니다. 예를 들어 get가 될 수있다 :

public int? CategoryId { 
    get {return innerObject.CategoryId;} 
} 

innerObjectnull이 될 수; 당신이 다른 4 명을 없애면,이 것을 최후의 수단으로 보아라.