大数据JavaWeb之MySQL基础---约束

约束:

下面具体来学习一下。

非空约束:not null,值不能为null。

创建表时添加约束:

咱们创建一个新表,添加非空约束,如下:

CREATE TABLE stu(
    id INT,
    NAME VARCHAR(20) NOT NULL -- name为非空
);

此时看一下表结构就可以看到name有一个非空约束:

此时咱们用这个可视化的工具来添加一条非空的数据,肯定能正常添加上:

而如果添加一个name为null的数据则会报错:

删除name的非空约束:

 

此时再看一下是否name的非空约束已经被删掉了:

此时就又可以添加空数据了:

创建表完后,添加非空约束:

实际使用时可能会碰到对已经创建好表的某个字段要修改其约束,所以这里用这种方式来添加一下非空约束:

 

唯一约束:unique,值不能重复。

创建表时,添加唯一约束:

这里先把之前的stu表删掉,再重新创建一个:

咱们来试一下,如果添加重复的手机号是否会报错:

【注意】:mysql中,唯一约束限定的列的值可以有多个null,下面添加多个为null的手机号试一下:

确实是这样的。

删除唯一约束:

 

在创建表后,添加唯一约束:

在删除唯一约束之后,咱们再来添加一下:

主键约束:primary key。

注意:

  • 含义:非空且唯一。
  • 一张表只能有一个字段为主键。
  • 主键就是表中记录的唯一标识。

在创建表时,添加主键约束:

删除主键:

 

创建完表后,添加主键:

自动增长: 

  • 概念:如果某一列是数值类型的,使用 auto_increment 可以来完成值得自动增长。
  • 在创建表时,添加主键约束,并且完成主键自增长。

    接下来则插入下数据:
  • 删除自动增长。

    此时再添加数据时就不会自动增长了:

  • 添加自动增长。 

外键约束:foreign key,让表于表产生关系,从而保证数据的正确性。

  • 在创建表时,可以添加外键

    接下来实践之前先创建一个新表:

    CREATE TABLE emp (
        id INT PRIMARY KEY AUTO_INCREMENT,
        NAME VARCHAR(30),
        age INT,
        dep_name VARCHAR(30),
        dep_location VARCHAR(30)
    );
    -- 添加数据
    INSERT INTO emp (NAME, age, dep_name, dep_location) VALUES ('张三', 20, '研发部', '广州'); INSERT INTO emp (NAME, age, dep_name, dep_location) VALUES ('李四', 21, '研发部', '广州'); INSERT INTO emp (NAME, age, dep_name, dep_location) VALUES ('王五', 20, '研发部', '广州');
    INSERT INTO emp (NAME, age, dep_name, dep_location) VALUES ('老王', 20, '销售部', '深圳'); INSERT INTO emp (NAME, age, dep_name, dep_location) VALUES ('大王', 22, '销售部', '深圳'); INSERT INTO emp (NAME, age, dep_name, dep_location) VALUES ('小王', 18, '销售部', '深圳');


    以上数据的缺点如下:
    1、数据冗余:

     2、后期还会出现增删改的问题,要改的话则得改多处。
    解决方案就是将其重复的拆分到一张单独的表,然后利用外键约束来进行信息关联,如下:

    所以基于这样的思路,则重新创建表如下:

    -- 解决方案:分成 2 张表
    -- 创建部门表(id,dep_name,dep_location)
    -- 一方,主表
    CREATE TABLE department(
     id INT PRIMARY KEY AUTO_INCREMENT,
     dep_name VARCHAR(20),
     dep_location VARCHAR(20)
    );
    -- 创建员工表(id,name,age,dep_id)
    -- 多方,从表
    CREATE TABLE employee(
    id INT PRIMARY KEY AUTO_INCREMENT, NAME VARCHAR(20),
    age INT,
    dep_id INT -- 外键对应主表的主键
    )
    -- 添加2个部门
    INSERT INTO department VALUES(NULL, '研发部','广州'),(NULL, '销售部', '深圳'); 
    SELECT * FROM department;
    -- 添加员工,dep_id 表示员工所在的部门
    INSERT INTO employee (NAME, age, dep_id) VALUES ('张三', 20, 1);
    INSERT INTO employee (NAME, age, dep_id) VALUES ('李四', 21, 1); 
    INSERT INTO employee (NAME, age, dep_id) VALUES ('王五', 20, 1);
    INSERT INTO employee (NAME, age, dep_id) VALUES ('老王', 20, 2); 
    INSERT INTO employee (NAME, age, dep_id) VALUES ('大王', 22, 2); 
    INSERT INTO employee (NAME, age, dep_id) VALUES ('小王', 18, 2);
    SELECT * FROM employee;

     

     以上两张表之间木有任何关系,则会有如下的问题:当我们在employee的dep_id里面输入不存在的部门,数据依然可以添加.但是并没有对应的部门:

    , 实际应用中不能出现这种情况。employee 的 dep_id 中的数据只能是 department 表中存在的 id。所以此时约束一下dep_id只能是department表中已经存在的id,所以接下来则需要给表添加外键约束了。咱们先将目前存在的表都删掉,因为要重新加上外键约束之后再来创建:

    什么是外键约束?
     
    好,此时咱们修改一下SQL语句,加入外键约束:

    -- 解决方案:分成 2 张表
    -- 创建部门表(id,dep_name,dep_location)
    -- 一方,主表
    CREATE TABLE department(
     id INT PRIMARY KEY AUTO_INCREMENT,
     dep_name VARCHAR(20),
     dep_location VARCHAR(20)
    );
    -- 创建员工表(id,name,age,dep_id)
    -- 多方,从表
    CREATE TABLE employee(
    id INT PRIMARY KEY AUTO_INCREMENT, NAME VARCHAR(20),
    age INT,
    dep_id INT, -- 外键对应主表的主键
    CONSTRAINT emp_dept_fk FOREIGN KEY (dep_id) REFERENCES department(id)
    );
    -- 添加2个部门
    INSERT INTO department VALUES(NULL, '研发部','广州'),(NULL, '销售部', '深圳'); 
    SELECT * FROM department;
    -- 添加员工,dep_id 表示员工所在的部门
    INSERT INTO employee (NAME, age, dep_id) VALUES ('张三', 20, 1);
    INSERT INTO employee (NAME, age, dep_id) VALUES ('李四', 21, 1); 
    INSERT INTO employee (NAME, age, dep_id) VALUES ('王五', 20, 1);
    INSERT INTO employee (NAME, age, dep_id) VALUES ('老王', 20, 2); 
    INSERT INTO employee (NAME, age, dep_id) VALUES ('大王', 22, 2); 
    INSERT INTO employee (NAME, age, dep_id) VALUES ('小王', 18, 2);
    SELECT * FROM employee;

    此时如果删除主表时,则会报错了:

     而如果在从表中插入一个父表中木有的部门ip则也会出错:

  • 删除外键
    ALTER TABLE 表名 DROP FOREIGN KEY 外键名称;

    此时咱们添加数据就可以随意写了:

  • 创建表之后,添加外键
    ALTER TABLE 表名 ADD CONSTRAINT 外键名称 FOREIGN KEY (外键字段名称) REFERENCES 主表名称(主表列名称);
  • 级联操作
    对于上面有外键约束的情况下,又有一个新问题出来了:
    “要把部门表中的 id 值 2,改成 5,能不能直接更新呢?”,咱们来试一下:

    那“要删除部门 id 等于 1 的部门, 能不能直接删除呢?”,下面来试一下:

    有一个比较笨的办法能解决这个问题,比如还是将部门id为2的改为5,可以这样做,先将从表id=2的设置的NULL,对于外键是可以设置为NULL的,如下:

    然后再将depart=1的改为5:

    最后再将从表的dep_id外键的值改为5:

    太麻烦了,这样操作,那有没有一种我要改顺带主从表都一起变的机制呢?级联操作就产生了,先来看一下啥叫级联?

     下面则具体来学习一下,在正式学习之前先来学习一个mysql的一个使用技巧,就是可以直观的来观测表之间的约束关系的,如下:

    先来打开这个设计器:

    然后把我们想看到表直接拖到窗口中来,比如我们想看一下给department和employee添加的外键约束的关系:

    所以有了这个利器,在未来表很多的时候,想要看表与表之间的关系用这个视图就比较方便了,好,接下来正式来学习下级联操作。

    1、添加级联操作:

    2、分类:

    ①、级联更新:ON UPDATE CASCADE
    下面来给咱们的表增加级联更新:

     此时咱们将那个部门id为5的又改成1,看这次能否直接成功?


    ②、级联删除:ON DELETE CASCADE
    接下来则来加一个级联删除,来满足当删除部门为1时,它相关的员工记录也被删除了,做法跟级联更新类似:

     然后咱们来删一下,看能否将员工对应的这个部门也给一并删掉了?

     

     确实达到了级联的目的,但是对于级联删除其实是很危险的,而且效率也不高,在实际使用时得要非常的谨慎。

posted on 2019-12-30 19:39  cexo  阅读(190)  评论(0编辑  收藏  举报

导航