Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/sql-server/23.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Sql 编写查询以规范化表_Sql_Sql Server_Tsql_Normalization - Fatal编程技术网

Sql 编写查询以规范化表

Sql 编写查询以规范化表,sql,sql-server,tsql,normalization,Sql,Sql Server,Tsql,Normalization,我需要编写查询以规范化表 我当前拥有的表具有以下属性:表名dbo.oldTable: CUS_ID STATE CITY ZIP CUS_PHONE CUS_NAME 1 OH ABC 11111 1111111111 G 2 IL DEG 33212 1233123123 H 3 CA ETE 55555 6666666666 E //many many more

我需要编写查询以规范化表

我当前拥有的表具有以下属性:表名
dbo.oldTable

CUS_ID  STATE   CITY    ZIP     CUS_PHONE   CUS_NAME
1       OH      ABC     11111   1111111111  G
2       IL      DEG     33212   1233123123  H
3       CA      ETE     55555   6666666666  E
//many many more lines of data
...................
我想在这里实现的是创建一个名为
territory
的新表,该表将包含
STATE
CITY
ZIP

到目前为止,我编写了以下查询,但显然它生成了很多行,并且找不到与原始表的连接

CREATE TABLE dbo.Territory
(STATE nvarchar(255), CITY nvarchar(255),ZIP nvarchar(255));

INSERT INTO dbo.Territory(STATE,CITY,ZIP)
SELECT STATE,CITY,ZIP FROM dbo.oldTable;
这样做正常吗?我使用的是MS SQL Server 2014

CREATE TABLE dbo.Territory
(id int identity, STATE nvarchar(255), CITY nvarchar(255),ZIP nvarchar(255));

create table dbo.customer (CUS_ID int identity, territoryid int,        CUS_PHONE varchar (12),  CUS_NAME varchar(25))

alter table dbo.customer  
ADD CONSTRAINT t_id,
FOREIGN KEY (territoryid) 
REFERENCES   dbo.Territory(id)
任何territoryid都必须引用dbo.territory中id列中已存在的值

To insert a new customer:
insert into dbo.customer (territoryid, cus_phone, cus_name) values (3,'212-555-1212','Mary')

我不完全确定邮政编码在美国是如何工作的,但假设一个州可以有多个城市,一个城市可以有多个邮政编码,我会做以下工作来规范数据库

CREATE TABLE States
( 
  StateID INT NOT NULL PRIMARY KEY IDENTITY(1,1)
, StateName NVARCHAR(100)
)
GO

CREATE TABLE City
( 
  CityID  INT NOT NULL PRIMARY KEY IDENTITY(1,1)
, StateID INT REFERENCES States(StateID)
, City    NVARCHAR(100)
)
GO

CREATE TABLE Zip
( 
  ZipID  INT NOT NULL PRIMARY KEY IDENTITY(1,1)
, CityID INT REFERENCES City(CityID)
, Zip    NVARCHAR(100)
)
GO
现在,您的客户表将看起来像

CUS_ID  ZIP_ID     CUS_PHONE   CUS_NAME
1       11111      1111111111     G
2       33212      1233123123     H
3       55555      6666666666     E

你的问题没有多大意义。您的原始表似乎没有被反规范化。但这似乎是名为inventory的表的一部分,在这种情况下,它被极度非规范化。如果您想获得规范化数据结构的真正帮助,您应该发布整个表结构。@SeanLange是的,它包含关于客户的信息和关于地域的信息。您为什么不规范化为一个包含
州的表和一个包含
城市的表(正如M.Ali和我同时键入的)?不幸的是,代码比你想象的要奇怪得多。@Lamak从张贴的小片段中可以轻松地成为客户主表。如果我有一个状态表,我会使状态代码成为外键。只是说,根据该表实际包含的内容,它可能会被规范化,也可能不会被规范化。在State或City上可能不需要使用Unicode(NVARCHAR)。Varchar应该可以。请记住,您需要尽可能窄的数据类型。我会使stateChar(2),Zip INT,cus_phone BIGINT。此外,你应该将客户名称分为FirstName和LastName,以使其规范化。我理解。但我需要的是将ZIP、STATE和CITY放在一个表中这违反了规范化规则本身,一个州可以有多个城市,所以你将重复一个州,该州有多少个城市,再加上每个城市有多少邮政编码。请注意,规范化的全部目的是减少数据冗余,正如您所建议的,最好保持数据的原样。在美国(以及世界其他地区),稍微进行一点非规范化是可以的,特别是当涉及到客户地址数据时。@SeanLange是真的,但如果有人不厌其烦地问了一个关于规范化的问题,这个人应该得到关于最佳实践的答案:)100%同意。除此之外没有其他建议。我同意你的看法,原来的结构可能还不错。Alis解决方案是正确的(就三阶形式而言),但有时太多的规范化(像大多数事情一样)不一定是正确的。