Database design 数据库设计101

Database design 数据库设计101,database-design,Database Design,关于数据库的设计,我有一个非常基本的问题。我原以为我知道答案,但在看到关于三重下拉菜单的在线教程和演示数据库的设计后,我不再那么确定了 好的,这是设置,涉及三个表 第一张表:TBL国家 字段:国家/地区id 国家 第二张表:tblstate 字段:state\u id 国家识别号 陈述 第三张表:tblcity 字段:cidy_id 州id 城市 现在我的问题是:在表3中,是否也需要包含countryid?通过使用SQL,您可以查询城市所在的国家……或者在城市表中引用国家是一种好的设计吗 我希望

关于数据库的设计,我有一个非常基本的问题。我原以为我知道答案,但在看到关于三重下拉菜单的在线教程和演示数据库的设计后,我不再那么确定了

好的,这是设置,涉及三个表

第一张表:TBL国家 字段:国家/地区id 国家

第二张表:tblstate 字段:state\u id 国家识别号 陈述

第三张表:tblcity 字段:cidy_id 州id 城市

现在我的问题是:在表3中,是否也需要包含countryid?通过使用SQL,您可以查询城市所在的国家……或者在城市表中引用国家是一种好的设计吗

我希望有人能帮忙:-)

在表3中,是否也需要包含countryid

没有

您可以使用以下查询获取县id:

SELECT country_id 
FROM tblcity c
INNER JOIN tblstate s ON (c.state_id = s.state_id)
如果您在城市表中包含
国家/地区id
,则您的数据库违反了正常格式,因为数据重复,而且数据可能会失去同步。例如,
tableCity
中的
country\u id
tableState
中的不匹配时会发生什么情况

如果您想获得国家名称,还需要加入该国:

SELECT co.country
FROM tblcity ci
INNER JOIN tblstate s ON (ci.state_id = s.state_id)
INNER JOIN tblCountry co ON (s.country_id = co.country_id)

还要注意,划分:
城市->州->国家
是一个非常以美国为中心的视图,并非所有国家都是这样划分的,在某些国家,您需要四个层次

简短回答,99.9%的正确率:不。您已经通过州记录获得了该国的参考资料

长答案,在0.1%的情况下:您可能需要从城市直接引用国家,因为您有很多关于国家城市的查询,向查询中添加第二个表将使查询花费更长的时间

诚然,第二种情况不太可能出现在城市、州和国家的记录集上,但对于其他类型的数据,如果您管理大量记录,则很可能出现这种情况

编辑:在我的工作中,我有很多这样的情况,我只是在表中保留三到四级引用的额外字段。这些是巨大的数据库,在所有常见查询中放置中间表确实会给数据库带来压力(每个查询使用的内存要多得多)。因此,我将从没有直接引用开始,然后根据需要添加“快捷方式”字段。这涉及到解决可伸缩性问题,这远远超出了初学者的问题。此外,如果您在下游表格中添加快捷方式字段,则这是应用程序的额外断点(当您将一个城市更新为另一个国家时,需要更新两条记录),因此请记住这一点。

标准化从数据开始。在下面的内容中,把state这个词理解得松散一些。我说的是数据分析和规范化,而不是政治等级的建模

country_name               state_name  city_name
--
United States of America   Alabama     Birmingham
United States of America   California  Atascadero
United States of America   Florida     Key Largo
United States of America   Illinois    Carbondale
United States of America   Kentucky    Winchester
United States of America   Michigan    St. Louis
United States of America   Ohio        Coldwater
United States of America   Montana     Glasgow
United States of America   Louisiana   Jefferson
United States of America   Wisconsin   Jefferson
Bulgaria                   Montana     Montana
Costa Rica                 San José    San José
Argentina                  Entre Rios  San José
Uruguay                    San José    San José de Mayo
它的意思是“城市[城市名称]位于国家[国家名称]的州[州名称]。”(表的意思称为其谓词。)

此表有效地将城市的“全名”标识为{国家名称、州名称、城市名称}。在概念层面上,它与使用{last_name,middle_name,first_name}来识别一个人没有太大区别。不同之处在于,尽管两个人经常有相同的全名,但两个城市却没有

很明显,只有一个候选键:{国家名,州名,城市名}。这张桌子是5NF的。用ID号代替文本无法改变这一点

现在,在将一个表规范化为5NF,并且该表被证明是“所有键”之后,您首先想到的是什么?是不是“好吧,现在我需要把键拆分成更多的表?”

我希望不是

要提高数据完整性,可以选择列的子集,并设置外键引用。以这种方式使用的投影对原始表的正常形式绝对没有影响。如果在这种投影之前它在2NF,那么在这种投影之后它将在2NF。这些表的谓词与原始表略有不同。(嗯。)

要选择要填充下拉列表的国家,您可以

select country_name
from countries
order by country_name;
用户选择了一个国家,选择州是很简单的

select state_name
from states
where country_name = '?'
order by state_name;
选择城市名称也是一样的

select city_name 
from cities
where country_name = '?' 
  and state_name = '?'
order by city_name;

谢谢这就是我的想法,也是我从所有的书中都能猜到的。在教程lol中看到这个设置真的让我很困惑。这说明了我的数据库设计知识有多么扎实;-)谢谢这证实了我的怀疑。我知道如果需要的话,我可以创建一个结合所有3个表的视图,但是看到这个设置我感到非常困惑。我实际上正在处理一个带有农场名称的数据库,所以这些表在某种程度上满足了我的需要。前两个表将与这里讨论的前两个表一样简单,但我的“城市”表将包含更多字段,如gps坐标。我明白你的意思,但在你开始显示的表中,如果其中一个州有两个城市名称值,该怎么办?您设置它的方式似乎合乎逻辑,不应该进一步规范化它,但如果要进一步规范化它并添加更多数据,它将需要多一个表?还是我错了?我对这一切都很陌生:-)@user1088537:关键是{国家名称、州名称、城市名称};在给定的州中,可以有任意数量的不同城市名称。该表不允许一个州有两个同名城市。我已经在SQL数据库中使用地址25年了;我从来没有在一个州见过两个同名的城市。(我在一个州见过两个同名的地方,它们不是一回事。)
select city_name 
from cities
where country_name = '?' 
  and state_name = '?'
order by city_name;