首页 > 3NF(第三范式)存在的问题?

3NF(第三范式)存在的问题?

如下图,这个表满足第三范式:

但是,依然存在以下问题:

数据冗余:多个“水果”
插入异常:“水果”分类下若没有产品(苹果、香蕉等),则看不到“水果”分类。
删除异常:删除了“白菜”,那么“蔬菜”类就看不到了,找不到这个分类了。
更新异常:更新“水果”为“fruit”,则需要更新多行数据。

可见,满足3NF,同样存在多种异常与冗余。
那么,我们怎么才能更好的设计数据库,使他们不存在这些异常?


你这个表不符合3NF。

首先,Id 不是主键,是人为定义的代理键(Surrogate Key).
数字 1 能唯一确定一个商品?

设计数据库首先从概念模型开始,然后是逻辑模型,最后才是物理模型。
代理键在物理实现时添加是没问题的,逻辑模型中处处用代理键会影响建模。

假设你的需求是记录商品的名称和类别。每个商品只能属于一个类别。
两个实体:Category, Product
它们的关系是:

每个Category可以包含1-n个Product,
每个Product属于1个Category

弄清楚了实体和关系,然后确定主键和属性。
如果一个Category只有一个名字,那名字就是很好的主键。
但根据你的描述,一个Category可以改名字,那到底什么才唯一确定一个Category呢?
答案还是要从需求中寻找。
假设每个Category对应一个Code,这个Code始终不变,那么Code就是主键。

Product也是一样。

参见如下数据模型:

数据冗余:多个“水果”
外键(Key) 不是冗余,是必要的

插入异常:“水果”分类下若没有产品(苹果、香蕉等),则看不到“水果”分类。
类别保存在Category表里

删除异常:删除了“白菜”,那么“蔬菜”类就看不到了,找不到这个分类了。
同上

更新异常:更新“水果”为“fruit”,则需要更新多行数据。
改变Name没关系,主键(Code)不能改,主键变了就变成另一个实体了。
主键通常是不会更新的。


插入的异常?没有商品也可以group by出分类啊,就现有表来说。

个人想法,如果想保留商品分类的话,拆分成两张表。
商品分类表,fid,分类名称。

商品表,id,name,fid。

满足第三范式。

【热门文章】
【热门文章】