2013-05-01 2 views
0

SQL WHERE 절에 문제가 있습니다 (SQL 2008 사용). 7 개의 매개 변수를 기반으로 결과 목록을 반환하는 저장 프로 시저를 만들어야하는데 그 중 일부는 null 일 수 있습니다. 문제가되는 것은 @element, @categories 및 @edu_id입니다. 그것들은 ID의리스트 일 수도, null 일 수도 있습니다. 매개 변수가 null이 아니면 내 where 절에서 내 특정 코드가 작동하는 것을 볼 수 있습니다. 그들이 null 인 경우 SQL을 코딩하는 방법을 잘 모르겠습니다. 필드는 데이터베이스의 INT입니다.SQL WHERE ... 가능하면 null 매개 변수가있는 IN 절

제 질문이 충분히 분명하기를 바랍니다. 여기에 내 질문이 있습니다.

BEGIN 
DECLARE @elements nvarchar(30) 
DECLARE @jobtype_id INT 
DECLARE @edu_id nvarchar(30) 
DECLARE @categories nvarchar(30) 
DECLARE @full_part bit 
DECLARE @in_demand bit 
DECLARE @lang char(2) 

SET @jobtype_id = null 
SET @lang = 'en' 
SET @full_part = null -- full = 1, part = 0 
SET @elements = '1,2,3' 
SET @categories = '1,2,3' 
SET @edu_id = '3,4,5' 

select 
jobs.name_en, 
parttime.fulltime_only, 
jc.cat_id category, 
je.element_id elem, 
jt.name_en jobtype, 
jobs.edu_id minEdu, 
education.name_en edu 
from jobs 
left join job_categories jc 
on (jobs.job_id = jc.job_id) 
left join job_elements je 
on (jobs.job_id = je.job_id) 
left join job_type jt 
on (jobs.jobtype_id = jt.jobtype_id) 
left join education 
on (jobs.edu_id = education.edu_id) 
left join 
(select job_id, case when (jobs.parttime_en IS NULL OR jobs.parttime_en = '') then 1 else 0 end fulltime_only from jobs) as parttime 
on jobs.job_id = parttime.job_id 
where [disabled] = 0  
and jobs.jobtype_id = isnull(@jobtype_id,jobs.jobtype_id) 
and fulltime_only = isnull(@full_part,fulltime_only) 
-- each of the following clauses should be validated to see if the parameter is null 
-- if it is, the clause should not be used, or the SELECT * FROM ListToInt... should be replaced by 
-- the field evaluated: ie if @elements is null, je.element_id in (je.element_id) 
and je.element_id IN (SELECT * FROM ListToInt(@elements,',')) 
and jc.cat_id IN (SELECT * FROM ListToInt(@categories,',')) 
and education.edu_id IN (SELECT * FROM ListToInt(@edu_id,',')) 

order by case when @lang='fr' then jobs.name_fr else jobs.name_en end; 

END 
+0

'WHERE .. @X IS NULL OR @X = COL ..' - 쿼리 플래너가 모든 것을 정렬합니다. – user2246674

+0

@ user2246674 -'OPTION (RECOMPILE)이 없다면 성능상 현명하지 않습니다. –

+0

@MartinSmith 아, 네, 좋은 지적입니다 - 계획에 영향을주고 사용 된 조인을 변경할 수 있습니다. 그러나 상수는 재 컴파일없이 여전히 폴드되지 않을 것인가? – user2246674

답변

2

and (@elements IS NULL OR je.element_id IN 
(SELECT * FROM ListToInt(@elements,','))) 
and (@categories IS NULL OR 
jc.cat_id IN (SELECT * FROM ListToInt(@categories,','))) 
.... 

같은 뭔가 트릭 각각

0
je.element_id IN (SELECT * FROM ListToInt(@elements,',')) OR @elements IS NULL 

그런 식으로 명시 적으로 NULL로 비교 봤어을해야합니까?

and (@elements is null or je.element_id IN (SELECT * FROM ListToInt(@elements,',')) 

등등.

0

에 대한