成人免费xxxxx在线视频软件_久久精品久久久_亚洲国产精品久久久_天天色天天色_亚洲人成一区_欧美一级欧美三级在线观看

SQL Server如何保證可空字段中非空值唯一

數據庫 SQL Server
文章闡述了編者同學遇到的SQL Server中一個關于“如何保證可空字段中非空值唯一”的問題,以及編者給出的幾種解決方式。

今天同學向我提了一個問題,是SQL Server中一個關于“如何保證可空字段中非空值唯一”的問題,我覺得蠻有意思,現記錄下來大家探討下。

問題是:在一個表里面,有一個允許為空的字段,空是可以重復的,但是不為空的值需要唯一。

表結構如下面代碼創建

  1. CREATE TABLE test_tb  
  2. (  
  3.     TestId int not null identity(1,1) primary key,  
  4.     Caption nvarchar(100) null 
  5. );  
  6. GO  
 

#p#

解決方案:

解決方案1:

對于這個問題,大家的第一個想法可能是:在Caption這個字段上面加一個唯一鍵不就可以了嗎?好,我們按著這個思路做下去,先創建唯一索引。

  1. CREATE UNIQUE NONCLUSTERED INDEX un_test_tb   
  2. ON test_tb(Caption)  
  3. GO  

 索引創建好了,我們來測試下效果

  1. INSERT INTO test_tb (Caption)  
  2. VALUES (null)  
  3. GO  
  4. INSERT INTO test_tb (Caption)  
  5. VALUES (null)  
  6. GO  

 運行之后我們會收到下面的錯誤信息:

  1. 消息 2601,級別 14,狀態 1,第 1 行  
  2. 不能在具有唯一索引 'un_test_tb' 的對象 'dbo.test_tb' 中插入重復鍵的行。  
  3. 語句已終止。  

 所以該解決方案是不行的。

解決方案2:

添加約束,讓SQL Server在插入數據的時候,先驗證下已有數據中是否有現在要插入的這個值。由于這個約束不是簡單的一個運算,因此我們先創建一個函數,然后再在約束中調用這個函數。

創建驗證邏輯函數:

  1. CREATE FUNCTION [dbo].[fn_CK_test_tb_Caption]()  
  2. RETURNS BIT 
  3. AS   
  4. BEGIN 
  5.     IF(EXISTS(  
  6.     SELECT    1  
  7.     FROM test_tb AS a  
  8.     WHERE (Caption IS NOT NULLAND EXISTS  
  9.       (SELECT 1 AS Expr1  
  10.         FROM test_tb  
  11.         WHERE (Caption IS NOT NULLAND (Caption = a.Caption) AND (a.TestId <> TestId))  
  12.      ))  
  13.         RETURN 0  
  14.       
  15.     RETURN 1  
  16. END 
  17. GO  

 在約束中引用函數:

  1. ALTER TABLE test_tb  
  2. ADD CONSTRAINT CK_test_tb_Caption CHECK (dbo.fn_CK_test_tb_Caption() = 1)  
  3. GO  
  4.  

 現在來測試下效果。先來測試NULL值
 

  1. INSERT INTO test_tb (Caption)  
  2. VALUES (null)  
  3. GO  
  4. INSERT INTO test_tb (Caption)  
  5. VALUES (null)  
  6. GO  
  7. SELECT * FROM test_tb  
  8. GO  

  可以成功運行,而且也出了多行為NULL的情況。現在再來測試不為空的插入情況。

  1. INSERT INTO test_tb (Caption)  
  2. VALUES (N'AAA')  
  3. GO  
  4. INSERT INTO test_tb (Caption)  
  5. VALUES (N'BBB')  
  6. GO  
  7. INSERT INTO test_tb (Caption)  
  8. VALUES (N'BBB')  
  9. GO  
  10. SELECT * FROM test_tb  
  11. GO  

 結果是在第三條語句的時候報錯了,表中的Caption字段也有'AAA'和'BBB'了,這也正好是我們要的結果。

所以解決方案2是正確的。但是為了這么一個小小功能,就寫這么長一段東西是不是太繁瑣了呢?我們來看下面的解決方案。

  解決方案3:(只適用于SQL Server 2008)

 SQL Server 2008中有了一個優雅的解決方案,那就是篩選索引。篩選索引是一種經過優化的非聚集索引,尤其適用于涵蓋從定義完善的數據子集中選擇數據的查詢。篩選索引使用篩選謂詞對表中的部分行進行索引。有了篩選索引,我們只需要寫一條語句就達到上面的效果。
 

  1. CREATE UNIQUE NONCLUSTERED INDEX un_test_tb   
  2. ON test_tb(Caption)  
  3. WHERE Caption is not null 
  4. GO  

 再用上面的一些測試語句來測試的話,會發現完全是達到了我們的要求。

這個方案的唯一缺點就是該語句只有SQL Server 2008支持。。

不知道各位有沒有又優雅又適用于各個版本的SQL Server的解決方案,望不勝賜教。

【編輯推薦】

  1. SQL Server 2000刪除實戰演習
  2. SQL Server存儲過程的命名標準如何進行?
  3. 卸載SQL Server 2005組件的正確順序
  4. 對SQL Server字符串數據類型的具體描述
  5. SQL Server數據類型的種類與應用


 

責任編輯:艾婧 來源: 博客園
相關推薦

2009-08-25 17:52:01

C#可空值類型

2010-07-06 10:25:16

SQL Server空

2017-01-13 23:06:45

swiftios

2010-07-02 13:26:56

SQL Server處

2010-09-13 16:39:36

sql server觸

2011-04-01 14:14:42

SQL Server空值

2010-11-12 14:39:36

Sql Server唯

2010-11-12 14:45:19

Sql Server唯

2024-05-24 09:29:28

2010-10-20 10:04:36

sql server自

2010-06-28 09:59:47

SQL Server自

2010-09-26 16:39:27

SQL子查詢

2021-11-15 06:56:45

系統運行空指針

2025-02-27 09:39:56

JavaJava 8對象

2020-08-18 22:20:49

vue.jsnullclass

2021-07-02 06:54:43

分布式環境ID

2012-03-07 10:00:35

2024-01-10 08:08:25

Python空值校驗開發

2010-09-24 17:08:03

SQL Server唯

2010-09-28 10:35:58

SQL字段默認值
點贊
收藏

51CTO技術棧公眾號

主站蜘蛛池模板: 国产一级视频在线 | 久久av网 | 国产女人与拘做受视频 | 亚洲一区二区av | 日本特黄a级高清免费大片 成年人黄色小视频 | 日韩一区二区免费视频 | 亚洲风情在线观看 | 91精品国产91久久久久久吃药 | 日本在线视频一区二区 | 久久久久99 | 2019精品手机国产品在线 | 国产精品成人一区 | 欧美一级在线免费观看 | 91久久精品一区二区二区 | 欧美性a视频 | 欧美性猛交一区二区三区精品 | 免费看黄视频网站 | 日韩精品一区二区三区在线播放 | 黄色成人在线观看 | 精品亚洲一区二区三区四区五区 | 亚洲成av人片在线观看无码 | 国产午夜精品一区二区三区四区 | 国产欧美一区二区三区久久手机版 | 91污在线 | 亚洲欧洲小视频 | 欧美日韩一区二区在线观看 | 午夜激情视频 | 韩国电影久久 | 日韩精品久久一区二区三区 | 91国在线观看 | 国产草草视频 | 99这里只有精品 | 国产欧美精品一区二区色综合朱莉 | 久久精品国产久精国产 | 欧美日韩一区二区在线 | 欧美日韩成人在线 | 欧美精品综合 | 亚洲高清免费 | 久久精品久久精品 | 亚洲精品久久久久久一区二区 | 午夜欧美日韩 |