首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >让int联接而不是字符串列更好吗?

让int联接而不是字符串列更好吗?
EN

Stack Overflow用户
提问于 2013-11-13 21:40:13
回答 5查看 2.9K关注 0票数 3

假设我有一个具有状态的用户,用户的状态可以是“活动的”、“暂停的”或“非活动的”。

现在,在创建数据库的时候,我在想.如果使用字符串值(使用枚举类型或应用规则)的列更好,那么查询和了解当前用户状态更容易,或者更好地连接,我应该加入一个包含可能的用户状态的UserStatuses表吗?

假设,应用程序用户当然不能创建状态。

编辑:澄清

  1. 我将不使用使用字符串联接,它将是到UserStatuses PK的int联接。
  2. 我最关心的是性能
  3. 可能的状态是静态的永远不会改变
EN

回答 5

Stack Overflow用户

回答已采纳

发布于 2013-11-13 21:44:37

在大多数系统上,它对性能几乎没有影响。就我个人而言,为了清晰起见,我会使用一个短字符串,并按照您的建议将其加入到一个包含更多细节的表中。

代码语言:javascript
运行
复制
create table intLookup
(
pk integer primary key,
value varchar(20) not null
)
insert into intLookup (pk, value) values
(1,'value 1'),
(2,'value 2'),
(3,'value 3'),
(4,'value 4')

create table stringLookup
(
pk varchar(4) primary key,
value varchar(20) not null
)

insert into stringLookup (pk, value) values
(1,'value 1'),
(2,'value 2'),
(3,'value 3'),
(4,'value 4')



create table masterData
(
stuff varchar(50),
fkInt integer references intLookup(pk),
fkString varchar(4)references stringLookup(pk)
)
create index i on masterData(fkInt)
create index s on masterData(fkString)

insert into masterData
(stuff, fkInt, fkString)
select COLUMN_NAME, (ORDINAL_POSITION %4)+1,(ORDINAL_POSITION %4)+1 from INFORMATION_SCHEMA.COLUMNS
go 1000

这将导致300 K行。

代码语言:javascript
运行
复制
select 
*
from masterData m inner join intLookup i on m.fkInt=i.pk

select 
*
from masterData m inner join stringLookup s on m.fkString=s.pk

在我的系统( Server)上-查询计划、I/O和CPU是相同的-执行时间是相同的。-只读取和处理一次查找表(在这两个查询中)

使用int或string没有区别。

票数 2
EN

Stack Overflow用户

发布于 2013-11-13 22:30:34

我认为,作为一个整体,每个人都找到了你问题答案的重要组成部分。但是,它们都有好的方面,应该放在一起,而不是分开。

  1. 正如生理学家所提到的,正常的标准化通常被认为是为了提高性能。然而,与逻辑学家不同的是,我认为你的情况是正常化的最佳时机。你的问题似乎是正常化问题。在这种情况下,使用Santhosh建议的数字键(然后返回包含状态解码的代码表)将导致每个记录存储的数据减少。这种差异不会显示在一个小型Access数据库中,但它可能会显示在一个拥有数百万记录的表中,每个记录都具有状态。
  2. 正如David所建议的那样,您可能会发现,将这个特定的数据点正常化将导致更受控制的最终用户体验。正常化状态字段还将允许您在稍后的某个位置编辑状态标志,并使该更改在整个数据库中永久化。如果您的老板和我的一样,那么您可能不得不将非活动状态更改为关闭状态(然后在下周再次返回),如果状态字段没有规范化,这将是更多的工作。通过规范化,还可以更容易地执行引用完整性。如果状态键不在状态代码表中,则无法将其添加到主表中。
  3. 如果您担心将来查询时的性能,那么有一些不同的事情要考虑。要回退状态,如果它是规范化的,您将向查询添加一个联接。在任何大小的记录集中,该连接可能不会对您造成伤害,但我相信它将通过限制必须处理的原始文本的数量来帮助更大的记录集。如果您主要关心的是查询数据时的性能,下面是关于如何优化查询的一个很好的资源:http://www.sql-server-performance.com/2007/t-sql-where/和我认为您会发现这里讨论的许多规则也将适用于在联接本身中强制执行的任何包含条件。

希望这能有所帮助!

克里斯托弗

票数 2
EN

Stack Overflow用户

发布于 2013-11-13 21:56:19

标准化背后的整个想法是防止数据重复(至少有一个概念)。

在这种情况下,用户一次只能拥有1种状态(我假设),所以他们没有理由将其放在自己的表中。你只会把事情复杂化。如果由于某种原因,这些状态不是静态的,那么您将有一个独立的表的唯一原因。意思是下个月你可以加上“有点活跃”和“可能不活跃”。这意味着,如果您没有将代码放在自己的表中,则需要更改代码以弥补这一点。您可以创建一个维护页面,用户可以在其中添加状态,然后需要创建一个独立的表。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/19964943

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档