始终使用nvarchar(MAX)有什么缺点吗?

时间:2020-03-06 14:52:17  来源:igfitidea点击:

在SQL Server 2005中,使所有字符字段都为nvarchar(MAX)而不是显式指定长度(例如,长度)有任何不利之处。 nvarchar(255)? (除了显而易见的那一句,我们无法在数据库级别限制字段长度)

解决方案

我发现的唯一问题是,我们在SQL Server 2005上开发应用程序,并且在一个实例中,我们必须支持SQL Server2000。我刚刚了解到,SQL Server 2000不喜欢varchar或者MAX选项的困难方式。 nvarchar。

这是一个公平的问题,除了明显的问题,他确实做了陈述。

缺点可能包括:

性能影响
查询优化器使用字段大小来确定最有效的执行计划

" 1.在扩展名和数据库页面中的空间分配是灵活的。因此,当使用更新向该字段添加信息时,如果新数据的长度大于先前插入的数据的长度,数据库将必须创建一个指针。数据库文件将变得零散=几乎所有性能(从索引到删除,更新和插入)的性能降低。"
http://sqlblogcasts.com/blogs/simons/archive/2006/02/28/Why-use-anything-but-varchar_2800_max_2900_.aspx

集成对其他系统很难知道如何与数据库集成的影响

不可预测的数据增长
可能的安全问题,例如我们可能会占用所有磁盘空间来使系统崩溃

这里有好文章:
http://searchsqlserver.techtarget.com/tip/1,289483,sid87_gci1098157,00.html

  • Varchar(最大)vs Varchar(255)

在MSDN论坛上提出了相同的问题:

When you store data to a VARCHAR(N) column, the values are physically stored in the same way. But when you store it to a VARCHAR(MAX) column, behind the screen the data is handled as a TEXT value. So there is some additional processing needed when dealing with a VARCHAR(MAX) value. (only if the size exceeds 8000)
  
  VARCHAR(MAX) or NVARCHAR(MAX) is considered as a 'large value type'. Large value types are usually stored 'out of  row'. It means that the data row will have a pointer to another location where the 'large value' is stored...

从原始帖子(那里有更多信息):

我有一个udf,它会填充字符串并将输出放入varchar(max)。如果直接使用此方法而不是将其转换为要调整的色谱柱的合适尺寸,则性能会很差。我最终将udf放到带有大音符的任意长度上,而不是依赖udf的所有调用方将字符串重新投射为较小的大小。

这将导致性能问题,尽管如果数据库很小,则可能永远不会导致任何实际问题。如果我们一次搜索大量记录,则每个记录将占用硬盘驱动器上的更多空间,并且数据库将需要读取磁盘的更多扇区。例如,一条小记录可能适合50个扇区,而一条大记录则适合5个扇区。使用大记录,我们需要从磁盘读取10倍的数据。

这将使屏幕设计更加困难,因为我们将无法预测控件的宽度。

有趣的链接:为什么可以在使用TEXT时使用VARCHAR?

它是关于PostgreSQL和MySQL的,因此性能分析是不同的,但是"显式性"的逻辑仍然成立:为什么要强迫自己始终担心与某事有关的事情呢?如果我们将电子邮件地址保存到变量中,则将使用"字符串"而不是"限于80个字符的字符串"。

一个问题是,如果必须使用多个版本的SQL Server,则MAX不会始终有效。因此,如果我们正在使用旧版DB或者涉及多个版本的任何其他情况,则最好格外小心。

有时,我们希望数据类型对其中的数据施加某种意义。

举例来说,我们有一列实际上不应超过20个字符。如果将该列定义为VARCHAR(MAX),则某些流氓应用程序可能会在其中插入一个长字符串,而我们永远不会知道,或者有任何防止它的方法。

下次应用程序使用该字符串时,假设该字符串的长度对于它所代表的域而言是适中且合理的,则我们将遇到无法预测且令人困惑的结果。

例如,当我们知道该字段将在5到10个字符的范围内设置时,这是个坏主意。我想如果不确定长度是多少,只会使用max。例如,电话号码永远不会超过一定数量的字符。

可以诚实地说,我们不确定表中每个字段的近似长度要求吗?

我的想法是正确的,这里是我肯定会考虑使用varchar(max)的一些字段。

Use varchar when the sizes of the
  column data entries vary considerably.
  Use varchar(max) when the sizes of the
  column data entries vary considerably,
  and the size might exceed 8,000 bytes.

有趣的是,MSDN文档对其进行了很好的总结:

这里有一个有趣的讨论。

可以将其视为另一个安全级别。我们可以在没有完全有效的外键关系的情况下设计表,并确保完全在业务层上存在关联实体。但是,外键被认为是良好的设计实践,因为外键会增加另一个约束级别,以防万一业务层出现混乱。字段大小限制也是如此,并且不使用varchar MAX。

遗留系统支持。如果我们有一个正在使用数据的系统,并且预期长度是一定的,则数据库是实施该长度的好地方。这不是理想的选择,但是传统系统有时并不理想。 = P

如果一行中的所有数据(对于所有列)都不会合理地占用8000个或者更少的字符,则数据层的设计应强制执行此操作。

数据库引擎效率更高,可以将所有内容都排除在Blob存储之外。我们可以限制行越小越好。我们可以在页面中填充的行越多越好。当数据库必须访问较少的页面时,它的性能会更好。

不使用max或者text字段的原因是我们无法执行在线索引重建,即即使使用SQL Server Enterprise Edition也可以使用ONLINE = ON进行重建。

数据库的工作是存储数据,以便企业可以使用它。使数据有用的一部分是确保数据有意义。允许某人输入无限数量的姓氏并不能确保有意义的数据。

段落数量不匹配