2010-06-11 34 views
8

经常建议选择尽可能窄的数据库字段大小。我想知道在SQL Server 2005 VARCHAR列中适用的程度:在VARCHAR(255)字段中存储10个字母的英语单词不会占用比VARCHAR(10)字段更多的存储空间。为什么使用较短的VARCHAR(n)字段?

是否有其他原因来限制VARCHAR字段的大小以尽可能贴近数据的大小?我正在考虑

  • 性能:在选择,过滤和排序数据时使用较小的n有没有优势?
  • 内存,包括应用程序端(C++)?
  • 风格/验证:您认为限制colunm大小以强制非感性数据导入失败(例如200个字符的姓氏)有多重要?
  • 还有什么?

背景:我帮助数据集成商将数据流设计成数据库支持的系统。他们必须使用限制他们选择数据类型的API。对于字符数据,只有VARCHAR(n)与n < = 255可用; CHAR,NCHAR,NVARCHARTEXT不是。我们正试图制定一些“良好实践”规则,如果真的有损于使用VARCHAR(255)甚至对于实际最大尺寸不会超过30字节左右的数据,问题就出现了。

一张表的典型数据量为1-10 Mio记录,最多可包含150个属性。查询性能(SELECT,经常有广泛的WHERE条款)和应用程序端检索性能是最重要的。

回答

13
  1. 数据完整性 - 到目前为止最重要的原因。如果您创建一个名为Surname的列是255个字符,那么您可能会获得比姓氏更多的列。你会得到名字,姓氏,中间名。你会得到他们最喜欢的宠物。你会得到“爱丽丝在会计部门的三角头发”。简而言之,您将使用户更容易将该列用作笔记/姓氏列。你想要上限来阻止那些试图将某个姓氏以外的东西放入该列的用户。如果您有一列要求特定长度的列(例如,美国的税收标识符是九个字符),但列是varchar(255),其他开发人员会想知道正在发生什么,您可能也会收到垃圾数据。

  2. 索引和行限制。在SQL Server中,您有8060个字节的IIRC限制。许多含有大量数据的脂肪非varchar(max)列可以快速超过该限制。另外,索引宽度IIRC有900字节的上限。所以,如果你想索引你的姓氏列和其他一些包含大量数据的人,你可能会超过这个限制。

  3. 报告和外部系统。作为报表设计器,您必须假定如果列的最大长度为255,则它可以包含255个字符。如果用户可以做到这一点,他们会做到这一点。因此,要说,“它可能不会超过30个字符。”甚至不是“不能超过30个字符”。永远不要依赖前者。作为一名报表设计师,您必须解决用户将大量数据输入到列中的可能性。这或者意味着截断值(如果是这种情况,为什么还要有额外的空间?)或者使用CanGrow来制作可爱的报告。无论哪种方式,如果列大小与存储的实际数据相距太远,那么您会让其他开发人员更难以理解列的意图。

+0

第二项为+1。 – 2010-06-11 20:55:39

+0

说得很好。 – HLGEM 2010-06-11 22:06:35

3

我认为最大的问题是数据验证。如果您允许姓氏为255个字符,那么您的数据库中将会有一个姓氏为200个以上的字符。

另一个原因是,如果您允许数据​​库保存255个字符,您现在必须在每个触及数据库的系统中考虑这种可能性。例如,如果您导出为固定宽度的列文件,则所有列的宽度必须为255个字符,这可能非常烦人,甚至有问题。这只是一个可能导致问题的例子。

+0

我也在想整体的行数可能是个问题。尽管在SQL Server 2005中允许超过8KB的行,但它可能会影响性能 - 页面本身仍然是8K,从我记忆中来看,它的执行方式有点不合理。所以,如果你在任何地方使用大列,你就有更多的危险超过8K页。 其他人对性能影响有更多了解吗? – 2010-06-11 15:04:41

+0

是的,如果超过了8060字节的限制,那么最大的可变长度列将被移动到另一个位置,并且指针被添加到原始页面记录中。这只会在变量列的真实大小(而不是声明大小)超过8060字节时才会发生。如果你为几个列分配VARCHAR(8000),但它们都只保存几个字符的数据,那么你就不会有这个问题。但它可能会发生。 – 2010-06-11 15:12:37

+0

非常感谢 - 你是第一个讨论行长的人,这是我错过的关键信息。我将托马斯的答案标记为“正确”,因为未来的读者更容易阅读。 – chryss 2010-06-11 20:24:29

0

一个很好的原因是验证。

(例如)在荷兰,一个社会安全号码总是9个字符长,当你不允许更多时它永远不会发生。

如果您允许更多和不明原因有10个字符,您需要输入支票(否则您不会)检查它是否长9。

0

1)可读性&支持

数据库开发人员可以看到一个名为StateCode用VARCHAR的长度字段(2),并得到了什么样的数据是场的一个好主意持有,甚至没有看内容。

2)报告

当数据是不带长度约束,期待开发者执行该列的数据的长度是所有类似。在报告这些数据时,如果开发人员未能使列数据保持一致,那么这会使数据不一致的报告看起来很有趣。

3)SQL Server数据存储

到8K“页面”,并从性能的角度来看它是理想的是尽可能有效和尽可能多的数据可能存储在页上的SQL Server存储数据。

如果您的数据库旨在将每个字符串列存储为varchar(255),那么“坏”数据可能会滑入其中一个字段中(例如,状态名称可能会滑入StateCode字段中,该字段的意思是2个字符长),并导致不必要的页面和索引拆分效率不高。

相关问题