首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 數據庫知識 >  >> SQL Server 資料庫 >> 關於SqlServer

SQL Server NULL 值處理三大陷阱:計數、空表值、外鍵驗證

     編輯:關於SqlServer

NULL 在 SQL Server 中代表「未知」而非「空」,處理不當易導致邏輯錯誤。本文針對三大常見情境說明正確作法。

陷阱一:COUNT(*) 與 COUNT(欄位) 差異

  • COUNT(欄位):忽略 NULL,僅計算非空值筆數
  • COUNT(*):計算所有列,包含 NULL
  • 需統計含 NULL 的總筆數時,用 COUNT(ISNULL(欄位, 0)) 替換

實測範例

CREATE TABLE xCount (pkey1 INT IDENTITY PRIMARY KEY, Col1 INT NULL)
INSERT xCount (Col1) VALUES (10), (15), (20), (NULL)

SELECT
  AVG(Col1) AS AvgWithoutIsNull,           -- 15 (忽略 NULL)
  AVG(ISNULL(Col1,0)) AS AvgWithIsNull,   -- 11 (NULL 視為 0)
  COUNT(Col1) AS CntCol1,                 -- 3
  COUNT(ISNULL(Col1,0)) AS CntIsNull,     -- 4
  COUNT(*) AS CntAll                      -- 4
FROM xCount

陷阱二:可為 NULL 的外鍵與參考完整性

父表主鍵不為 NULL,但子表外鍵允許 NULL 時,DRI(宣告式參考完整性)不會強制子表外鍵必須有對應父表值。此時子表可存入 NULL,導致「孤兒記錄」邏輯上合法但業務上異常。

解決方案:加入 CHECK 約束

ALTER TABLE Child
ADD CONSTRAINT CK_Child_Parent_NotNull
CHECK (ParentPkey1 IS NOT NULL)

或允許 NULL 但需驗證:

CHECK (ParentPkey1 IS NULL OR ParentPkey1 IN (SELECT pkey1 FROM Parent))

陷阱三:複合主鍵作為可為 NULL 的外鍵

當父表為複合主鍵(PK1, PK2),子表外鍵允許 NULL 時,可能出現 FK1=有效值, FK2=NULL 的異常組合。需加入多欄位 CHECK 約束:

CHECK (
  (FK1 IS NULL AND FK2 IS NULL) OR
  (FK1 IS NOT NULL AND FK2 IS NOT NULL AND EXISTS (...))
)

最佳實務原則

  1. 聚合函數涉及 NULL 時,明確使用 ISNULL/COALESCE
  2. 外鍵欄位預設設為 NOT NULL,業務真正允許「未知」時再放寬
  3. 複合外鍵必須加入 CHECK 約束防止部分 NULL 異常

正確理解 NULL 語意,配合約束與函數,才能建立資料品質可靠的資料庫系統。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved