답변:
CASE 문 사용
UPDATE : 이전 구문 (몇 사람이 지적한대로)이 작동하지 않습니다. 다음과 같이 CASE를 사용할 수 있습니다.
WHERE OrderNumber LIKE
CASE WHEN IsNumeric(@OrderNumber) = 1 THEN
@OrderNumber
ELSE
'%' + @OrderNumber
END
또는 @ NJ Reed 와 같은 IF 문을 사용할 수 있습니다 .
CASE
대부분의 경우 적절한 솔루션을 사용하는 것이 좋습니다. 필자의 경우 비교 연산자를 변경하고 싶었으므로 다음 접근 방식을 사용했습니다.
IF 또는 CASE 없이이 작업을 수행 할 수 있어야합니다
WHERE
(IsNumeric(@OrderNumber) AND
(CAST OrderNumber AS VARCHAR) = (CAST @OrderNumber AS VARCHAR)
OR
(NOT IsNumeric(@OrderNumber) AND
OrderNumber LIKE ('%' + @OrderNumber))
SQL의 특징에 따라 내재 된 캐스트가 지원되는지 여부에 따라 주문 번호의 캐스트를 INT 또는 VARCHAR로 조정해야 할 수도 있습니다.
이것은 WHERE 절에서 매우 일반적인 기술입니다. WHERE 절에 "IF"논리를 적용하려면 부울 AND가있는 추가 조건을 적용 할 섹션에 추가하면됩니다.
IF 문이 전혀 필요하지 않습니다.
WHERE
(IsNumeric(@OrderNumber) = 1 AND OrderNumber = @OrderNumber)
OR (IsNumeric(@OrderNumber) = 0 AND OrderNumber LIKE '%' + @OrderNumber + '%')
where (@AdmUserId is null or CurrentOrder.CustomerAdmUserId = @AdmUserId)
또는 전용 필터의 경우 IncludeDeleted = 0 : where (@IncludeDeleted = 1 or ItemObject.DeletedFlag = 0)
SQL에서 이것을 수행하는 좋은 방법은 없습니다. 내가 본 몇 가지 접근법 :
1) 부울 연산자와 결합 된 CASE를 사용하십시오.
WHERE
OrderNumber = CASE
WHEN (IsNumeric(@OrderNumber) = 1)
THEN CONVERT(INT, @OrderNumber)
ELSE -9999 -- Some numeric value that just cannot exist in the column
END
OR
FirstName LIKE CASE
WHEN (IsNumeric(@OrderNumber) = 0)
THEN '%' + @OrderNumber
ELSE ''
END
2) SELECT 외부에서 IF 사용
IF (IsNumeric(@OrderNumber)) = 1
BEGIN
SELECT * FROM Table
WHERE @OrderNumber = OrderNumber
END ELSE BEGIN
SELECT * FROM Table
WHERE OrderNumber LIKE '%' + @OrderNumber
END
3) 긴 문자열을 사용하여 조건부로 SQL 문을 작성한 다음 EXEC를 사용하십시오.
세 번째 접근 방식은 끔찍하지만, 여러 가지 가변 조건이있는 경우 효과가있는 유일한 방법입니다.
IF...ELSE...
조건부를 부울 AND
및 로 변환하는 것 OR
입니다. ^이 방법의 단점은이 방법은 IF
많은 것이 있거나 중첩 된 것이 많으면 두뇌가 어려울 수 있다는 것입니다.
where ... like / = ... case ... then ... 부울과 함께 작동 할 수 있다고 생각합니다. T-SQL을 사용하고 있습니다.
시나리오 : bool이 거짓이면 Person-30의 취미를, bool이 참이면 Person-42의 취미를 원한다고 가정 해 봅시다. (일부에 따르면, 취미 조회는 비즈니스 계산주기의 90 % 이상을 구성하므로 가까운 지불금을 지불하십시오.)
CREATE PROCEDURE sp_Case
@bool bit
AS
SELECT Person.Hobbies
FROM Person
WHERE Person.ID =
case @bool
when 0
then 30
when 1
then 42
end;
어디서? (IsNumeric (@OrderNumber) <> 1 OR OrderNumber = @OrderNumber) AND (IsNumber (@OrderNumber) = 1 또는 '%'와 같은 OrderNumber + @ 주문 번호 + '%')
IF P THEN Q ELSE R
<=>
( ( NOT P ) OR Q ) AND ( P OR R )
CASE 문은 항상 IF 보다 더 나은 옵션 입니다.
WHERE vfl.CreatedDate >= CASE WHEN @FromDate IS NULL THEN vfl.CreatedDate ELSE @FromDate END
AND vfl.CreatedDate<=CASE WHEN @ToDate IS NULL THEN vfl.CreatedDate ELSE @ToDate END
WHERE OrderNumber LIKE CASE WHEN IsNumeric(@OrderNumber) = 1 THEN @OrderNumber ELSE '%' + @OrderNumber END
경우에 따라 조건이 제대로 작동합니다.
다음 예제는 부울 표현식의 일부로 쿼리를 실행 한 다음 부울 표현식의 결과에 따라 약간 다른 명령문 블록을 실행합니다. 각 명령문 블록은 BEGIN으로 시작하고 END로 완료됩니다.
USE AdventureWorks2012;
GO
DECLARE @AvgWeight decimal(8,2), @BikeCount int
IF
(SELECT COUNT(*) FROM Production.Product WHERE Name LIKE 'Touring-3000%' ) > 5
BEGIN
SET @BikeCount =
(SELECT COUNT(*)
FROM Production.Product
WHERE Name LIKE 'Touring-3000%');
SET @AvgWeight =
(SELECT AVG(Weight)
FROM Production.Product
WHERE Name LIKE 'Touring-3000%');
PRINT 'There are ' + CAST(@BikeCount AS varchar(3)) + ' Touring-3000 bikes.'
PRINT 'The average weight of the top 5 Touring-3000 bikes is ' + CAST(@AvgWeight AS varchar(8)) + '.';
END
ELSE
BEGIN
SET @AvgWeight =
(SELECT AVG(Weight)
FROM Production.Product
WHERE Name LIKE 'Touring-3000%' );
PRINT 'Average weight of the Touring-3000 bikes is ' + CAST(@AvgWeight AS varchar(8)) + '.' ;
END ;
GO
중첩 된 IF ... ELSE 문 사용 다음 예는 IF… ELSE 문을 다른 명령문 안에 중첩하는 방법을 보여줍니다. 각 명령문을 테스트하려면 @Number 변수를 5, 50 및 500으로 설정하십시오.
DECLARE @Number int
SET @Number = 50
IF @Number > 100
PRINT 'The number is large.'
ELSE
BEGIN
IF @Number < 10
PRINT 'The number is small'
ELSE
PRINT 'The number is medium'
END ;
GO
If @LstTransDt is Null
begin
Set @OpenQty=0
end
else
begin
Select @OpenQty=IsNull(Sum(ClosingQty),0)
From ProductAndDepotWiseMonitoring
Where Pcd=@PCd And PtpCd=@PTpCd And TransDt=@LstTransDt
end
이것이 도움이되는지보십시오.
USE AdventureWorks2012;
GO
IF
(SELECT COUNT(*) FROM Production.Product WHERE Name LIKE 'Touring-3000%' ) > 5
PRINT 'There are more than 5 Touring-3000 bicycles.'
ELSE PRINT 'There are 5 or less Touring-3000 bicycles.' ;
GO