SQL 約束 (Constraints)


引言

--• NOT NULL
--• UNIQUE
--• PRIMARY KEY
--• FOREIGN KEY
--• CHECK
--• DEFAULT

 

1.SQL NOT NULL 約束

1.1、強制 "Id_P" 列和 "LastName" 列不接受 NULL 值(默認為NULL)

CREATE TABLE Persons
(
Id_P int NOT NULL,
LastName varchar(255) NOT NULL,
FirstName varchar(255),
Address varchar(255),
City varchar(255)
)

 

 

2.SQL UNIQUE 約束

2.1、在 "Persons" 表創建時在 "Id_P" 列創建 UNIQUE 約束

CREATE TABLE Persons
(
Id_P int NOT NULL,
LastName varchar(255) NOT NULL,
FirstName varchar(255),
Address varchar(255),
City varchar(255),
UNIQUE (Id_P)
)

 

或者:

CREATE TABLE Persons
(
Id_P int NOT NULL UNIQUE,
LastName varchar(255) NOT NULL,
FirstName varchar(255),
Address varchar(255),
City varchar(255)
)

 

2.2、如果需要命名 UNIQUE 約束,以及為多個列定義 UNIQUE 約束

CREATE TABLE Persons
(
Id_P int NOT NULL,
LastName varchar(255) NOT NULL,
FirstName varchar(255),
Address varchar(255),
City varchar(255),
CONSTRAINT UQ_PersonID UNIQUE (Id_P,LastName)
)

 

2.3、當表已被創建時,如需在 "P_Id" 列創建 UNIQUE 約束

ALTER TABLE Persons ADD UNIQUE (P_Id)

 

2.4、需命名 UNIQUE 約束,並定義多個列的 UNIQUE 約束

ALTER TABLE Person    
ADD CONSTRAINT UQ_PersonID UNIQUE (P_Id,LastName)

 

2.5、撤銷 UNIQUE 約束

ALTER TABLE Persons
DROP CONSTRAINT UQ_PersonID

 

 

 

3.SQL PRIMARY KEY 約束

--主鍵必須包含唯一的值。
--主鍵列不能包含 NULL 值。
--每個表應該都一個主鍵,並且每個表只能有一個主鍵。

3.1、在 "Persons" 表創建時在 "Id_P" 列創建 PRIMARY KEY約束

--1
CREATE TABLE Persons
(
Id_P int NOT NULL,
LastName varchar(255) NOT NULL,
FirstName varchar(255),
Address varchar(255),
City varchar(255),
PRIMARY KEY (Id_P)
)

--2
CREATE TABLE Persons
(
Id_P int NOT NULL PRIMARY KEY,
LastName varchar(255) NOT NULL,
FirstName varchar(255),
Address varchar(255),
City varchar(255)
)

 

3.2、需要命名 PRIMARY KEY 約束,以及為多個列定義 PRIMARY KEY 約束

CREATE TABLE Persons
(
Id_P int NOT NULL,
LastName varchar(255) NOT NULL,
FirstName varchar(255),
Address varchar(255),
City varchar(255),
CONSTRAINT PK_PersonID PRIMARY KEY (Id_P,LastName)
)

 

3.3、在表已存在的情況下為 "Id_P" 列創建 PRIMARY KEY 約束

ALTER TABLE Persons
ADD PRIMARY KEY (Id_P)

 

3.4、需要命名 PRIMARY KEY 約束,以及為多個列定義 PRIMARY KEY 約束

ALTER TABLE Persons
ADD CONSTRAINT PK_PersonID PRIMARY KEY (Id_P,LastName)

 

3.5、撤銷 PRIMARY KEY 約束

ALTER TABLE Persons
DROP CONSTRAINT PK_PersonID

 

 

 

4.SQL FOREIGN KEY 約束

--一個表中的 FOREIGN KEY 指向另一個表中的 PRIMARY KEY

4.1、在 "Orders" 表創建時為 "Id_P" 列創建 FOREIGN KEY

CREATE TABLE Orders
(
O_Id int NOT NULL PRIMARY KEY,
OrderNo int NOT NULL,
Id_P int FOREIGN KEY REFERENCES Persons(Id_P)
)

 

4.2、需要命名 FOREIGN KEY 約束,以及為多個列定義 FOREIGN KEY 約束

CREATE TABLE Orders
(
O_Id int NOT NULL,
OrderNo int NOT NULL,
Id_P int,
PRIMARY KEY (O_Id),
CONSTRAINT FK_PerOrders FOREIGN KEY (Id_P)
REFERENCES Persons(Id_P)
)

 

4.3、在 "Orders" 表已存在的情況下為 "Id_P" 列創建 FOREIGN KEY 約束

ALTER TABLE Orders
ADD FOREIGN KEY (Id_P)
REFERENCES Persons(Id_P)

 

4.4、需要命名 FOREIGN KEY 約束,以及為多個列定義 FOREIGN KEY 約束

ALTER TABLE Orders
ADD CONSTRAINT FK_PerOrders
FOREIGN KEY (Id_P)
REFERENCES Persons(Id_P)

 

4.5、撤銷 FOREIGN KEY 約束

ALTER TABLE Orders
DROP CONSTRAINT FK_PerOrders

 

【高級應用】

-- 創建測試主表. ID 是主鍵.
-- 班級表.
CREATE TABLE test_main_class (
  id      INT   NOT NULL,
  value   VARCHAR(20),
  PRIMARY KEY(id)  
);


-- 創建測試子表. 
-- 學生表.
CREATE TABLE test_sub_student (
  id      INT  NOT NULL,
  main_id INT  DEFAULT 0,
  value   VARCHAR(10),
  PRIMARY KEY(id)  
);


-- 插入測試主表數據.
INSERT INTO test_main_class(id, value) VALUES (0, '暫無班級');
INSERT INTO test_main_class(id, value) VALUES (1, '2015級123班');
INSERT INTO test_main_class(id, value) VALUES (2, '2015級124班');


-- 插入測試子表數據.
INSERT INTO test_sub_student(id, main_id, value) VALUES (1, 1, '陌軒');
INSERT INTO test_sub_student(id, main_id, value) VALUES (2, 2, '思夢'); 

默認外鍵約束方式

ALTER TABLE test_sub_student ADD CONSTRAINT main_id_cons FOREIGN KEY (main_id) REFERENCES test_main_class; 

添加外鍵后,在刪除數據(運行結果會提示錯誤,因為test_mian_class的數據已經給test_sub_student使用) 

DELETE test_main_class WHERE ID = 1;

 刪除外鍵約束 

ALTER TABLE test_sub_student DROP CONSTRAINT main_id_cons;

 

 

DELETE CASCADE 方式

-- 創建外鍵(使用 ON DELETE CASCADE 選項,刪除主表的時候,同時刪除子表)
ALTER TABLE test_sub_student ADD CONSTRAINT main_id_cons
FOREIGN KEY (main_id) REFERENCES test_main_class ON DELETE CASCADE;

 

測試刪除(刪除成功后select查看2表運行結果)

DELETE test_main_class WHERE ID = 1;

測試完畢后,刪除 外鍵約束

ALTER TABLE test_sub_student DROP CONSTRAINT main_id_cons;

 

 

UPDATE CASCADE方式

--更新主表的主鍵時候,同時更新子表外鍵
ALTER TABLE test_sub_student
ADD CONSTRAINT main_id_cons
FOREIGN KEY (main_id) REFERENCES test_main_class ON UPDATE CASCADE;

SET NULL方式

-- 創建外鍵(使用 ON DELETE SET NULL 選項,刪除主表的時候,同時將子表的 main_id 設置為 NULL)
ALTER TABLE test_sub_student
ADD CONSTRAINT main_id_cons
FOREIGN KEY (main_id) REFERENCES test_main_class ON DELETE SET NULL;

 SET DEFAULT 方式

--首先測試 ON DELETE SET DEFAULT
ALTER TABLE test_sub_student
ADD CONSTRAINT fk_main_class
FOREIGN KEY (main_id)  REFERENCES  test_main_class ON DELETE SET DEFAULT;
SELECT
test_main_class.value AS "班級",
test_sub_student.value AS "學生"
FROM
test_main_class
JOIN test_sub_student
ON(test_main_class.id = test_sub_student.main_id);

--班級                   學生
-------------------- ----------
--2015級123班              陌軒
--2015級124班              思夢

DELETE FROM test_main_class WHERE ID = 1;

SELECT
test_main_class.value AS "班級",
test_sub_student.value AS "學生"
FROM
test_main_class
JOIN test_sub_student
ON(test_main_class.id = test_sub_student.main_id);

--班級                   學生
-------------------- ----------
--暫無班級               陌軒
--2015級124班              思夢

ON DELETE SET DEFAULT
指定如果試圖刪除某一行,
而該行的鍵被其他表的現有行中的外鍵所引用,
則組成被引用行中的外鍵的所有值將被設置為它們的默認值。
為了執行此約束,目標表的所有外鍵列必須具有默認定義。
如果某個列可為空值,並且未設置顯式的默認值,則將使用 NULL 作為該列的隱式默認值。
因 ON DELETE SET DEFAULT 而設置的任何非空值在主表中必須有對應的值,才能維護外鍵約束的有效性。

--然后測試 ON UPDATE SET DEFAULT
--刪除前面的外鍵約束.
ALTER TABLE test_sub_student DROP CONSTRAINT fk_main_class; 
-- 創建外鍵約束.
ALTER TABLE test_sub_student
ADD CONSTRAINT fk_main_class
FOREIGN KEY (main_id)  REFERENCES  test_main_class ON UPDATE SET DEFAULT;

UPDATE test_main_class SET ID = 20 WHERE ID = 2;


SELECT
test_main_class.value AS "班級",
test_sub_student.value AS "學生"
FROM
test_main_class
JOIN test_sub_student
ON(test_main_class.id = test_sub_student.main_id);
--班級                     學生
-------------------- ----------
--暫無班級                 陌軒
--暫無班級                 思夢

ON UPDATE SET DEFAULT
指定如果試圖更新某一行,
而該行的鍵被其他表的現有行中的外鍵所引用,
則組成被引用行中的外鍵的所有值將被設置為它們的默認值。
為了執行此約束,目標表的所有外鍵列必須具有默認定義。
如果某個列可為空值,並且未設置顯式的默認值,則將使用 NULL 作為該列的隱式默認值。
因 ON UPDATE SET DEFAULT 而設置的任何非空值在主表中必須有對應的值,才能維護外鍵約束的有效性。

 

 

5.SQL CHECK 約束

5.1、規定 "Id_P" 列必須只包含大於 0 的整數

CREATE TABLE Persons
(
Id_P int NOT NULL CHECK (Id_P>0),
LastName varchar(255) NOT NULL,
FirstName varchar(255),
Address varchar(255),
City varchar(255)
)

 

5.2、需要命名 CHECK 約束,以及為多個列定義 CHECK 約束

CREATE TABLE Persons
(
Id_P int NOT NULL,
LastName varchar(255) NOT NULL,
FirstName varchar(255),
Address varchar(255),
City varchar(255),
CONSTRAINT CK_Person CHECK (Id_P>0 AND City='Sandnes')
)

 

5.3、在表已存在的情況下為 "Id_P" 列創建 CHECK 約束

ALTER TABLE Persons
ADD CHECK (Id_P>0)

 

5.4、需要命名 CHECK 約束,以及為多個列定義 CHECK 約束

ALTER TABLE Persons
ADD CONSTRAINT CK_Person CHECK (Id_P>0 AND City='Sandnes')

 

5.5、撤銷 CHECK 約束

ALTER TABLE Persons
DROP CONSTRAINT CK_Person

 

 

【備注:CHECK示例】

1.檢查只能是男或者女
add const ck_sex check(sex in('男,女')),
add const ck_sex check(sex ='男' or sex ='女')


2.在一個范圍中間
constraint ch_age check(sage>0 and sage<120),
add const ck_age check(age between 12 and 30)


3.長度大於某個值
add const ck_lenght check(len(lenght)>6)


4.數大於某個值
add const ck_number ckeck(number>1)


5.只能是8位字符,前兩位是 0 ,3~4位為數字,第 5 位為下划線,6~8位為字母
alter table 表名
add constraint chkk check((字段 like '00[0-9][0-9]/_[a-z,A-Z][a-z,A-Z][a-z,A-Z]%' escape '/')and(len(字段)=8) )
或者是
alter table 表名
add constraint chkk check((字段 like '00[0-9][0-9][_][a-z,A-Z][a-z,A-Z][a-z,A-Z]%')and(len(字段)=8) )


6.電子郵箱要含有@符號
check(字段like '%@%')


7.SQL中用check約束一列的首字母為's'
check(col1 like 's%')


8.檢查約束前3位和后8位均為數字字符:
check(col2 like '[0-9][0-9][0-9]%[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]')


9.如何建立檢查身份證的約束,身份證是18位,最后一位還有可能是X
select 身份證號 from 表名
where len(身份證號) = 18 and (right(身份證號,17) like '[0-9]'or right(身份證號,17) like 'x')


10.如何設置區號由0-9之間的數字組成
CONSTRAINT quhao CHECK (quhao LIKE '[0-9][0-9][0-9]'
or quhao LIKE '[0-9][0-9][0-9][0-9]'or quhao LIKE '[0-9][0-9][0-9][0-9][0-9]'));
解釋: 其中quhao LIKE '[0-9]...[0-9]'的號碼由表示n位從0到9中的數組成。
quhao LIKE '[0-9][0-9][0-9]' 表示3位的區號,如北京010;quhao LIKE '[0-9][0-9][0-9][0-9]'表示4位的區號,如三門峽0398; quhao LIKE
'[0-9][0-9][0-9][0-9][0-9]'表示5位的區號,如香港00852

 

11.最后回復時間 TLastClickT 發貼時間 TTime
最后回復時間 必須晚於 發貼時間 並且小於等於當前時間 使用GetDate()函數獲取當前時間
設計表
在TLastClickT上右擊
選擇約束,新建,填入
([TLastClickT] > [TTime] and [TLastClickT] < GetDate())
或者
TiastReply(回帖時間)大於Ttime(發帖時間)在創表的同時
創建表的時候應該還沒有回帖吧,為什么要用默認值?
可以添加一個約束 alter table topic alter column add check(TlastReply is null or TlastReply > Ttime)

 

12.定義前八位為數字或者 -
一共是15位,為CHAR型
alter table 表名
add constraint chk check(字段 like'[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]%'),
constraint chklen check(len(字段)=15)

 

13.如何限制varchar字段不允許出現單引號的檢查約束 !!!
設表為TALBENAME,不能有引號的字段為FIELDNAME 則:
ALTER TABLE tablename ADD CONSTRAINT CK_fieldname CHECK (not fieldname like '%''%')

 

14.在表中的某列中通過檢查約束,讓其有某些固定的值
check(sid like 'bd[0-9][0-9][0-9][0-9][0-9][0-9]')
add const ck_num check(num like '[1][2] [4][_] [0-9][0-9] [0-9][a-z]')

 

15.如何限制varchar字段不允許出現字符串的檢查約束 !!!
設表名為TABLENAME,VARCHAR類型的字段為VAR_FIELD.則有:
ALTER TABLE [dbo].[TABLENAME] ADD CONSTRAINT [CK_TABLENAME] CHECK (isnumeric([VAR_FIELD]) = 1)
這樣,在VAR_FIELD只要出現字段一旦出現非數字內容就會報告錯誤。

 

16.電話號碼的格式必須為xxxx-xxxxxxxx或手機號11位
alter 表名 add constraint ck_字段名 check (字段 like '[0-9][0-9][0-9][0-9]_[0-9]......' or len(字段)=11)

 

17.身份證號是18位且唯一的
alter 表名 add
constraint ck_字段名 check (len(字段名)=18 ),
constraint uq_字段名 unique(字段名)

 

 

6.SQL DEFAULT 約束

6.1、在 "Persons" 表創建時為 "City" 列創建 DEFAULT 約束

CREATE TABLE Persons
(
Id_P int NOT NULL,
LastName varchar(255) NOT NULL,
FirstName varchar(255),
Address varchar(255),
City varchar(255) DEFAULT 'Sandnes'
)

通過使用類似 GETDATE() 這樣的函數,DEFAULT 約束也可以用於插入系統值

CREATE TABLE Orders
(
Id_O int NOT NULL,
OrderNo int NOT NULL,
Id_P int,
OrderDate date DEFAULT GETDATE()
)

 

6.2、在表已存在的情況下為 "City" 列創建 DEFAULT 約束

alter table Persons 
add constraint DF_Persons  default ('SANDNES') for City

 

6.3、撤銷 DEFAULT 約束

ALTER TABLE Persons
DROP CONSTRAINT DF_Persons

 

 

作者:陌軒君 
出處:http://www.cnblogs.com/yuan-jun/p/6505562.html
本文版權歸作者和博客園共有,歡迎轉載,但未經作者同意必須保留此段聲明,且在文章頁面明顯位置給出原文連接,否則保留追究法律責任的權利。

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM