数据库主键和外键

            刚开始学数据库的时候,刚接触到的一个较为陌生的概念就是主键和外键。啥叫主键,从字面意思上来看感觉一脸懵。简单点说主键就类似每个人的身份证,代表一个唯一的某个人,而且主键不能为空,估计你也没见过哪个人没有身份证的。

             那外键是啥,一个表中的某一个或多个字段是关联另一个表的主键,那我们把这一个或多个字段称为这个表的外键,外键可以是这个表的主键也可以不是。外键的作用是保证引用数据的完整性。

            来看看书上是怎么定义主键的。主键:又称主码,是表中一列或多列的组合。下面来展示如何创建主键。

 create table stu( id int PRIMARY KEY, name varchar(10), hobby varchar(20) );
Query OK, 0 rows affected (0.03 sec)

mysql> show create table stu;
+-------+----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| Table | Create Table                                                                                                                                                                     |
+-------+----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| stu   | CREATE TABLE `stu` (
  `id` int(11) NOT NULL,
  `name` varchar(10) DEFAULT NULL,
  `hobby` varchar(20) DEFAULT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 |
+-------+----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
1 row in set (0.00 sec)

主键id显示的是NOT NULL,PRIMARY KEY (`id`)表明id是主键,上面是单字段主键。

mysql> create table stu1( id int , name varchar(10), hobby varchar(20),primary key(id,name) );
Query OK, 0 rows affected (0.02 sec)

mysql> show create table stu1;
+-------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| Table | Create Table                                                                                                                                                                         |
+-------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| stu1  | CREATE TABLE `stu1` (
  `id` int(11) NOT NULL,
  `name` varchar(10) NOT NULL,
  `hobby` varchar(20) DEFAULT NULL,
  PRIMARY KEY (`id`,`name`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 |
+-------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
1 row in set (0.00 sec)

mysql> 

上面是多字段主键。

mysql> create table stu2( id int primary key, stu_id int, name varchar(20),constraint fk_stu foreign key(stu_id) references stu(id) );
Query OK, 0 rows affected (0.04 sec)

mysql> 
mysql> 
mysql> show create table stu2;
+-------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| Table | Create Table                                                                                                                                                                                                                                                                    |
+-------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| stu2  | CREATE TABLE `stu2` (
  `id` int(11) NOT NULL,
  `stu_id` int(11) DEFAULT NULL,
  `name` varchar(20) DEFAULT NULL,
  PRIMARY KEY (`id`),
  KEY `fk_stu` (`stu_id`),
  CONSTRAINT `fk_stu` FOREIGN KEY (`stu_id`) REFERENCES `stu` (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 |
+-------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
1 row in set (0.00 sec)

mysql> 

在表stu2上添加了fk_stu的外键约束,外键名称为stu_id,其依赖于表stu的主键id。下面来看外键保证引用数据的完整性 。

mysql> select * from stu2;
+----+--------+------+
| id | stu_id | name |
+----+--------+------+
|  1 |      1 | lisi |
+----+--------+------+
1 row in set (0.00 sec)

mysql> select * from stu;
+----+----------+-------+
| id | name     | hobby |
+----+----------+-------+
|  1 | zhangdan | daqiu |
+----+----------+-------+
1 row in set (0.00 sec)

上面是2个表中的数据。表stu2的外键stu_id和stu的主键一一对应。现在再想表stu2中插入数据。

mysql> insert into stu2 values(1,2,"wangwu");
ERROR 1062 (23000): Duplicate entry '1' for key 'PRIMARY'
mysql> 

插入记录报错了,因为表stu中没有id=2的记录。

mysql> insert into stu values(2,"wangwu","chifan");
Query OK, 1 row affected (0.00 sec)

mysql> select * from stu;
+----+----------+--------+
| id | name     | hobby  |
+----+----------+--------+
|  1 | zhangdan | daqiu  |
|  2 | wangwu   | chifan |
+----+----------+--------+
2 rows in set (0.00 sec)
mysql> insert into stu2 values(2,2,"zhaoliu");
Query OK, 1 row affected (0.00 sec)

mysql> select * from stu2;
+----+--------+---------+
| id | stu_id | name    |
+----+--------+---------+
|  1 |      1 | lisi    |
|  2 |      2 | zhaoliu |
+----+--------+---------+
2 rows in set (0.00 sec)

mysql> 

我们先向表stu表插入id=2的字段,再对stu2操作就成功了。主表先动,从表才能动。从表是含有外键约束的那个表,主表就是那个含有外键约束对应主键的那个表。再想想,如果试着删除某一行会发生啥。

mysql> delete * from stu2 where id=2;
ERROR 1064 (42000): You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '* from stu2 where id=2' at line 1
mysql> delete * from stu where id=2;
ERROR 1064 (42000): You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '* from stu where id=2' at line 1
mysql> 

不管对stu还是stu2进行删除操作都会失败,因为2个表已经有了约束关系,谁也离不开谁了。

 

 

 

 

 

  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

盼盼编程

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值