数据库设计三大范式

第一范式1NF:保证列的原子性

列数据的不可分割

两列的属性相近或相似或一样,尽量合并属性一样的列,确保不产生冗余数据。

错误案例:

create table student(
   sid int primary key,
   sname varchar(11),
   saddress varchar(200)
);
insert into student values(1,"韩梅梅","河南省郑州市二七区京广路街道新月家园1单元2000室");
insert into student values(2,"韩梅1","河南郑州二七区淮河路街道升龙国际2单元3001室");
-- 获取河南学生  对saddress需要进行截取

正确案例:

create table student(
   sid int primary key,
   sname varchar(11),
   saddress_province varchar(10),
   saddress_city varchar(10),
   saddress_street varchar(10),
   saddress_detail varchar(20)
);
insert into student values(1,"韩梅梅","河南省","郑州市","二七区京广路街道","新月家园1单元2000室");
insert into student values(2,"韩梅1","河南省","郑州市","二七区淮河路街道","升龙国际2单元3001室");

第二范式2NF:消除部分依赖(所有列必须完全依赖主键列)

只针对于联合主键

满足1NF后,要求表中的所有列,都必须依赖于主键,而不能有任何一列与主键没有关系,也就是说一个表只描述一件事情

错误案例:一个订单详情表

create table order_detail(
       order_id int comment  "订单编号",
       product_name varchar(11) comment "商品名字",
       product_number int comment "商品数量",
       product_price decimal comment "商品单价",
       discount  float comment "商品折扣",
       money decimal comment "总金额",
       constraint kf_2 foreign key (order_id) references order(order_id),
       primary key(order_id,product_name)
      
);
# product_price和discount 只依赖联合主键的product_name部分:
# 再定义一个商品表

可以看出表中的product_price和discount 只依赖联合主键的product_name部分:
因此需要再定义一个商品表

正确案例:把部分依赖product_name的信息写道商品表中

create table order_detail(
       order_id int comment  "订单编号",
       product_id int comment  "商品编号",
       product_number int comment "商品数量",
       money decimal comment "总金额",
       constraint kf_21 foreign key (order_id) references order(order_id),
       constraint kf_22 foreign key (product_id) references product(product_id),
       primary key(order_id,product_id)  
);
create table product(
       product_id int primary key comment "商品编号",
       product_name varchar(11) comment "商品名字",
       product_price decimal comment "商品单价",
       discount  float comment "商品折扣"
);

第三范式3NF:所有列必须直接依赖主键列

数据不能存在传递关系,即每个属性都跟主键有直接关系而不是间接关系。像:a-->b-->c  属性之间含有这样的关系,是不符合第三范式的。

错误案例:

create table student(
   sid int primary key,
   sname varchar(11),
   school_name varchar(11),
   school_address varchar(20),
   school_type  varchar(10),
   school_no    varchar(10)  
);
insert into student values(1,"韩梅梅","陇西路小学","河南省郑州市二七区","公立小学","NO10001");
insert into student values(3,"韩2","陇西路小学","河南省郑州市二七区","公立小学","NO10001");

问题:1:student包含了描述学生的信息 还 包含了描述学校的信息

​            2:同一个学校的学生记录中  学校的信息会出现多次

正确案例:把学校相关的学校定义为学校表  在学生表中引用学校表的主键即可

create table student(
   sid int primary key,
   sname varchar(11),
   schoolid varchar(11),
   constraint kf_1 foreign key (schoolid) references school(schoolid)
);
create table school(
   schoolid    varchar(11),
   school_name varchar(11),
   school_address varchar(20),
   school_type  varchar(10)
);
insert into student values(1,"韩梅梅","NO10001");
insert into student values(3,"韩2","NO10001");
insert into school values("NO10001","陇西路小学","河南省郑州市二七区","公立小学");

你可能感兴趣的:(mysql,数据库)