外鍵
外鍵概念
如果公共關(guān)鍵字在一個關(guān)系中是主關(guān)鍵字讳苦,那么這個公共關(guān)鍵字被稱為另一個關(guān)系的外鍵工禾。由此可見,外鍵表示了兩個關(guān)系之間的相關(guān)聯(lián)系俯在。以另一個關(guān)系的外鍵作主關(guān)鍵字的表被稱為主表搔确,具有此外鍵的表被稱為主表的從表彼棍。
在實際操作中,將一個表的值放入第二個表來表示關(guān)聯(lián)妥箕,所使用的值是第一個表的主鍵值(在必要時可包括復(fù)合主鍵值)滥酥。此時,第二個表中保存這些值的屬性稱為外鍵(foreign key)畦幢。
外鍵作用
保持數(shù)據(jù)一致性,完整性缆蝉,主要目的是控制存儲在外鍵表中的數(shù)據(jù),約束宇葱。使兩張表形成關(guān)聯(lián),外鍵只能引用外表中的列的值或使用空值刊头。
創(chuàng)建外鍵
建表時指定外鍵約束
-- 創(chuàng)建外鍵的方式一 : 創(chuàng)建子表同時創(chuàng)建外鍵
-- 年級表 (id\年級名稱)
CREATE TABLE `grade` (
`gradeid` INT(10) NOT NULL AUTO_INCREMENT COMMENT '年級ID',
`gradename` VARCHAR(50) NOT NULL COMMENT '年級名稱',
PRIMARY KEY (`gradeid`)
) ENGINE=INNODB DEFAULT CHARSET=utf8
-- 學生信息表 (學號,姓名,性別,年級,手機,地址,出生日期,郵箱,身份證號)
CREATE TABLE `student` (
`studentno` INT(4) NOT NULL COMMENT '學號',
`studentname` VARCHAR(20) NOT NULL DEFAULT '匿名' COMMENT '姓名',
`sex` TINYINT(1) DEFAULT '1' COMMENT '性別',
`gradeid` INT(10) DEFAULT NULL COMMENT '年級',
`phoneNum` VARCHAR(50) NOT NULL COMMENT '手機',
`address` VARCHAR(255) DEFAULT NULL COMMENT '地址',
`borndate` DATETIME DEFAULT NULL COMMENT '生日',
`email` VARCHAR(50) DEFAULT NULL COMMENT '郵箱',
`idCard` VARCHAR(18) DEFAULT NULL COMMENT '身份證號',
PRIMARY KEY (`studentno`),
KEY `FK_gradeid` (`gradeid`),
CONSTRAINT `FK_gradeid` FOREIGN KEY (`gradeid`) REFERENCES `grade` (`gradeid`)
) ENGINE=INNODB DEFAULT CHARSET=utf8
建表后修改
-- 創(chuàng)建外鍵方式二 : 創(chuàng)建子表完畢后,修改子表添加外鍵
ALTER TABLE `student`
ADD CONSTRAINT `FK_gradeid` FOREIGN KEY (`gradeid`) REFERENCES `grade` (`gradeid`);
刪除外鍵
操作:刪除 grade 表黍瞧,發(fā)現(xiàn)報錯
注意 : 刪除具有主外鍵關(guān)系的表時 , 要先刪子表 , 后刪主表
-- 刪除外鍵
ALTER TABLE student DROP FOREIGN KEY FK_gradeid;
-- 發(fā)現(xiàn)執(zhí)行完上面的,索引還在,所以還要刪除索引
-- 注:這個索引是建立外鍵的時候默認生成的
ALTER TABLE student DROP INDEX FK_gradeid;
DML語言
數(shù)據(jù)庫意義 : 數(shù)據(jù)存儲、數(shù)據(jù)管理
管理數(shù)據(jù)庫數(shù)據(jù)方法:
通過SQLyog等管理工具管理數(shù)據(jù)庫數(shù)據(jù)
通過DML語句管理數(shù)據(jù)庫數(shù)據(jù)
DML語言 :數(shù)據(jù)操作語言
用于操作數(shù)據(jù)庫對象中所包含的數(shù)據(jù)
包括 :
INSERT (添加數(shù)據(jù)語句)
UPDATE (更新數(shù)據(jù)語句)
DELETE (刪除數(shù)據(jù)語句)
添加數(shù)據(jù)
INSERT命令
語法:
INSERT INTO 表名[(字段1,字段2,字段3,...)] VALUES('值1','值2','值3')
注意 :
字段或值之間用英文逗號隔開 .
' 字段1,字段2...' 該部分可省略 , 但添加的值務(wù)必與表結(jié)構(gòu),數(shù)據(jù)列,順序相對應(yīng),且數(shù)量一致 .
可同時插入多條數(shù)據(jù) , values 后用英文逗號隔開 .
-- 使用語句如何增加語句?
-- 語法 : INSERT INTO 表名[(字段1,字段2,字段3,...)] VALUES('值1','值2','值3')
INSERT INTO grade(gradename) VALUES ('大一');
-- 主鍵自增,那能否省略呢?
INSERT INTO grade VALUES ('大二');
-- 查詢:INSERT INTO grade VALUE ('大二')錯誤代碼:1136
Column count doesn`t match value count at row 1
-- 結(jié)論:'字段1,字段2...'該部分可省略 , 但添加的值務(wù)必與表結(jié)構(gòu),數(shù)據(jù)列,順序相對應(yīng),且數(shù)量一致.
-- 一次插入多條數(shù)據(jù)
INSERT INTO grade(gradename) VALUES ('大三'),('大四');</pre>
練習題目
自己使用INSERT語句為課程表subject添加數(shù)據(jù) . 使用到外鍵.
修改數(shù)據(jù)
update命令
語法:
UPDATE 表名 SET column_name=value [,column_name2=value2,...] [WHERE condition];
注意 :
column_name 為要更改的數(shù)據(jù)列
value 為修改后的數(shù)據(jù) , 可以為變量 , 具體指 , 表達式或者嵌套的SELECT結(jié)果
condition 為篩選條件 , 如不指定則修改該表的所有列數(shù)據(jù)
where條件子句
可以簡單的理解為 : 有條件地從表中篩選數(shù)據(jù)
測試:
-- 修改年級信息
UPDATE grade SET gradename = '高中' WHERE gradeid = 1;
刪除數(shù)據(jù)
DELETE命令
語法:
DELETE FROM 表名 [WHERE condition];
注意:condition為篩選條件 , 如不指定則刪除該表的所有列數(shù)據(jù)
-- 刪除最后一個數(shù)據(jù)
DELETE FROM grade WHERE gradeid = 5
TRUNCATE命令
作用:用于完全清空表數(shù)據(jù) , 但表結(jié)構(gòu) , 索引 , 約束等不變 ;
語法:
TRUNCATE [TABLE] table_name;
-- 清空年級表
TRUNCATE grade
注意:區(qū)別于DELETE命令
相同 : 都能刪除數(shù)據(jù) , 不刪除表結(jié)構(gòu) , 但TRUNCATE速度更快
不同 :
使用TRUNCATE TABLE 重新設(shè)置AUTO_INCREMENT計數(shù)器
使用TRUNCATE TABLE不會對事務(wù)有影響 (事務(wù)后面會說)
測試:
-- 創(chuàng)建一個測試表
CREATE TABLE `test` (
`id` INT(4) NOT NULL AUTO_INCREMENT,
`coll` VARCHAR(20) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=INNODB DEFAULT CHARSET=utf8
-- 插入幾個測試數(shù)據(jù)
INSERT INTO test(coll) VALUES('row1'),('row2'),('row3');
-- 刪除表數(shù)據(jù)(不帶where條件的delete)
DELETE FROM test;
-- 結(jié)論:如不指定Where則刪除該表的所有列數(shù)據(jù),自增當前值依然從原來基礎(chǔ)上進行,會記錄日志.
-- 刪除表數(shù)據(jù)(truncate)
TRUNCATE TABLE test;
-- 結(jié)論:truncate刪除數(shù)據(jù),自增當前值會恢復(fù)到初始值重新開始;不會記錄日志.
-- 同樣使用DELETE清空不同引擎的數(shù)據(jù)庫表數(shù)據(jù).重啟數(shù)據(jù)庫服務(wù)后
-- InnoDB : 自增列從初始值重新開始 (因為是存儲在內(nèi)存中,斷電即失)
-- MyISAM : 自增列依然從上一個自增數(shù)據(jù)基礎(chǔ)上開始 (存在文件中,不會丟失)