2011-07-04 54 views
1

我有一個用戶函數返回一個BIT calle dbo.IsPartReady。 我試圖使用觸發器內部的功能如下:SQL Server:使用TSQL變量時出錯

SET @railReady = dbo.IsPartReady(1,@curPartiId); 
SET @frameReady = dbo.IsPartReady(2,@curPartiId); 
SET @dryAReady = dbo.IsPartReady(3,@curPartiId); 
SET @dryBReady = dbo.IsPartReady(4,@curPartiId); 

IF ((@railReady AND @frameReady) OR (@dryAReady AND @dryBReady)) 

,我發現了以下錯誤的IF語句: 在上下文指定的非布爾類型的表達式,其中一個條件是預計接近'AND'。

我在做什麼錯?

+0

局部變量的聲明?請顯示代碼 – heximal

+1

除非在'while'循環(* shudder *)或'cursor'循環(* double shudder *)中設置了'@ curPartiId',否則很可能觸發器在多行操作中被破壞也。 –

+1

達成一致的達米安(+1),除非沒有太大的差別(所以不知道爲什麼你不同地顫抖)。 while循環只是一個沒有DECLARE CURSOR的遊標。 –

回答

4

SQL Server中的BIT數據類型不是布爾值,而是整數。您必須將變量的值與某個值進行比較以獲取布爾表達式。 BIT可以具有值0,1或NULL。 http://msdn.microsoft.com/en-us/library/ms177603.aspx

declare @B bit = 1 

if @B = 1 
begin 
    print 'Yes' 
end 
3

使用以下:

IF ((@railReady = 1 AND @frameReady = 1) OR (@dryAReady = 1 AND @dryBReady = 1)) 

或替代,

IF ((@railReady & @frameReady) | (@dryAReady & @dryBReady)) = 1 

的更多信息:

爲了驗證這一點,我們可以使用包含的所有組合真值表四個bit值:

WITH B(x) AS (SELECT CAST(0 AS bit) UNION ALL SELECT CAST(1 AS bit)) 
, AllSixteenCombinations(a,b,c,d) AS 
    (SELECT * FROM B B1 CROSS JOIN B B2 CROSS JOIN B B3 CROSS JOIN B B4) 
SELECT a,b,c,d 
, CASE WHEN ((a = 1 AND b = 1) OR (c = 1 AND d = 1)) THEN 'Y' ELSE 'N' END[Logic] 
, CASE WHEN ((a & b) | (c & d)) = 1 THEN 'Y' ELSE 'N' END [Bitwise] 
FROM AllSixteenCombinations 

輸出:

以何種方式
a  b  c  d  Logic Bitwise 
----- ----- ----- ----- ----- ------- 
0  0  0  0  N  N 
0  1  0  0  N  N 
0  0  1  0  N  N 
0  1  1  0  N  N 
1  0  0  0  N  N 
1  1  0  0  Y  Y 
1  0  1  0  N  N 
1  1  1  0  Y  Y 
0  0  0  1  N  N 
0  1  0  1  N  N 
0  0  1  1  Y  Y 
0  1  1  1  Y  Y 
1  0  0  1  N  N 
1  1  0  1  Y  Y 
1  0  1  1  Y  Y 
1  1  1  1  Y  Y 

(16 row(s) affected) 
+0

對於第一個示例,強烈建議在合併AND和OR時始終使用括號。對於第二種,我不確定這是什麼語言,但我當然無法在T-SQL中獲得類似的工作。你能發佈你嘗試過的代碼的實際工作線嗎? –

+0

在2005年就像我的魅力一樣,有趣的+ 1 –