Database 如何设计优雅地表示地址的数据库模式?

Database 如何设计优雅地表示地址的数据库模式?,database,database-design,database-schema,Database,Database Design,Database Schema,我所说的地址只是指普通地址,如国家、州、市、区、街道、大楼、 地址可以在其他表(如people)中有效引用, 这样我们就可以选择同一个城市的人,等等? thx 这取决于您希望如何规范数据库、仓库或事务 例1: 非标准化,所有内容都在一张表中 表名:用户 属性:用户ID、用户名、国家/地区 要检索的sql: select username from user where country="USA" select username from user inner join country wh

我所说的地址只是指普通地址,如国家、州、市、区、街道、大楼、

地址可以在其他表(如people)中有效引用, 这样我们就可以选择同一个城市的人,等等?
thx

这取决于您希望如何规范数据库、仓库或事务

例1: 非标准化,所有内容都在一张表中

表名:用户

属性:用户ID、用户名、国家/地区

要检索的sql:

 select username from user where country="USA"
 select username from user inner join country where country="USA"
例2: 标准化,所有内容都在单独的表中

表名:用户 属性:userid、用户名、countryID

表名:国家 属性:countryID,国家名称

要检索的sql:

 select username from user where country="USA"
 select username from user inner join country where country="USA"

您需要知道db用于确定有效方式的用途。

根据我的经验,您需要国家、州、城市、邮政编码和地址

只有前三个/四个便于筛选用户。枚举字段非常适合前两个字段。接下来的两个都是理想的使用API进行验证的——这将省去您维护有效值列表的麻烦

我还没有遇到过任何系统,尽管我认为邮局会需要它,同时地理定位需要将地址部分分块到单独的数据块中,以便进行更精确的过滤——此外,每个用户都有自己的方式输入后者

记住,有些国家没有国家;其他人没有邮政编码;不同国家的邮政编码格式差异很大


还要记住,即使一个用户在您的系统中可以有多个地址,您最不希望的事情就是将多个用户绑定到同一地址。\u id。它们通常作为用户或其公司的详细信息,或作为与后者相关的1-n详细信息放在更好的位置;从来没有。如果没有,UI问题会很快出现,并且总会有人错误地编辑用户B的地址,因为后者恰好与用户A共享地址。

这里有一个用于地址表示的扩展数据库结构, 这种方法的优点 1.以后可以添加城市、国家或州。 2.它支持城市、国家或州的EDT。 3.城市映射到州,州映射到国家。因此,您只需将城市存储在addrss中。您不需要在每个地址中存储州和国家,从而减少冗余。 4.您可以在用户选择国家时生成一个状态列表。类似地,当用户选择一个州时,您可以生成一个城市列表

Address
   id            INT        PK    AUTO_INCREMENT
   street        VARCHAR    
   city_fk       INT        FK    
   Zip_code      VARCHAR
City
   id            INT        PK    AUTO_INCREMENT
   name          VARCHAR
   state_fk      INT        FK
State
   id            INT        PK    AUTO_INCREMENT
   name          VARCHAR
   country_fk    INT        Fk
Country
   id            INT        PK    AUTO_INCREMENT
   name          VARCHAR

user
   id            INT        PK    AUTO_INCREMENT
   # other details
user_address_mapping                              # So that user can have multiple address
   id            INT        PK    AUTO_INCREMENT
   user_fk       INT        FK                    # Link to user
   address_fk    INT        FK                    # Foreign key to address
编辑:感谢@Denis评论 或者,如果你的国家没有州,或者你想要一个通用的解决方案,这里是结构

Address
   id            INT        PK    AUTO_INCREMENT
   street        VARCHAR    
   city_fk       INT        FK    
   state_fk      INT        FK
   country_fk    INT        FK
   Zip_code      VARCHAR
City
   id            INT        PK    AUTO_INCREMENT
   name          VARCHAR
State
   id            INT        PK    AUTO_INCREMENT
   name          VARCHAR
Country
   id            INT        PK    AUTO_INCREMENT
   name          VARCHAR

user
   id            INT        PK    AUTO_INCREMENT
   # other details
user_address_mapping                              # So that user can have multiple address
   id            INT        PK    AUTO_INCREMENT
   user_fk       INT        FK                    # Link to user
   address_fk    INT        FK                    # Foreign key to address
   # Here user_fk & address_fk should be composite unique key, so that users can not share an address.

所以当一个国家没有州,它也不能有城市-您可以使用与国家同名的单个状态,请参见I am genius:P:对于解决方案1,如果我们需要按国家/地区的人搜索,将有许多连接从用户处到达国家/地区表,这会变得效率低下吗?同时,当我们使用或映射时,代码确实很长,像USEROBJECT.ADDRESS.CITY.STATE.COUNTRY,看起来有点不方便。对于解决方案2,通常我们会有一些级联下拉列表,第一个是COUNTRY,第二个是STATE,它不能反映这种关系,通常在用户选择国家时,我们应该展示这些状态。所以我想知道我们如何才能高效优雅地解决上述问题?thx@hetaoblog:使用第一种解决方案,如果一个国家没有任何州,只需添加一个与国家名称相同的虚拟州。在数据库查询缓存或使用APC/memcached等的服务器中缓存不太可能更改但经常需要的城市、州、国家的数据。缓存后,您将不需要许多联接,从而加快查询速度。可能重复