CHECKSUM()和BINARY_CHECKSUM()之间有什么区别?什么时候/什么是适当的使用场景?

And*_*rns 19 sql-server sql-server-2005

MSDN并没有真正用简单的英语解释确切的差异,或者何时选择其中一个的信息.

校验

返回通过表的行或表达式列表计算的校验和值.CHECKSUM旨在用于构建哈希索引.

BINARY_CHECKSUM

返回通过表的行或表达式列表计算的二进制校验和值.BINARY_CHECKSUM可用于检测对表行的更改.

它确实暗示应该使用二进制校验和来检测行更改,但不是为什么.

Joh*_*som 17

查看以下博客文章,重点介绍差异.

http://decipherinfosys.wordpress.com/2007/05/18/checksum-functions-in-sql-server-2005/

从此链接添加信息:

CHECKSUM函数的关键意图是基于表达式或列列表构建哈希索引.如果您使用它来计算和存储表级别的列以表示在表中使记录唯一的列上的校验和,那么这可以帮助确定行是否已更改.然后可以使用此机制而不是与使记录唯一的所有列连接以查看记录是否已更新.SQL Server联机丛书有很多关于此功能的示例.

使用这些功能时需要注意以下几点:

您需要确保要比较的两个校验和之间的列或表达式顺序相同,否则值将不同并将导致问题.

我们不建议使用校验和(*),因为以这种方式生成的值将基于运行时表定义的列顺序,这可以在一段时间内轻松更改.因此,明确定义列列表.

包含datetime数据类型列时要小心,因为粒度是1/300秒,即使很小的变化也会导致不同的校验和值.因此,如果必须使用日期时间数据类型列,请确保获得确切的日期+小时/分钟.即您想要的粒度级别.

您可以使用三种校验和功能:

CHECKSUM:这是上面描述的.

CHECKSUM_AGG:返回组中值的校验和,在这种情况下忽略Null值.这也适用于SQL Server 2005中新的分析函数的OVER子句.

BINARY_CHECKSUM:如名称所示,它返回通过行或表达式列表计算的二进制校验和值.CHECKSUM和BINARY_CHECKSUM之间的区别在于为字符串数据类型生成的值.这种差异的一个例子是为"DECIPHER"和"decipher"生成的值在BINARY_CHECKSUM的情况下会有所不同,但对于CHECKSUM函数则是相同的(假设我们对实例进行了不区分大小写的安装).另一个区别在于表达式的比较.如果两个表达式的元素具有相同的类型和字节表示,则BINARY_CHECKSUM()返回相同的值.因此,"2Volvo Director 20"和"3Volvo Director 30"将产生相同的值,但CHECKSUM()函数会评估类型以及比较两个字符串,如果它们相等,则只返回相同的值.

Example:
STRING              BINARY_CHECKSUM_USAGE    CHECKSUM_USAGE
------------------- ----------------------    -----------
2Volvo Director 20  -1356512636                -341465450
3Volvo Director 30  -1356512636                -341453853
4Volvo Director 40  -1356512636                -341455363
Run Code Online (Sandbox Code Playgroud)

  • 因此,在链接腐烂之前会更好,然后会更糟. (17认同)

小智 8

带有MD5的HASHBYTES比CHECKSUM慢5倍,我在一个行超过100万的表上进行了测试,并且每次测试运行5次以获得平均值.

有趣的是CHECKSUM与BINARY_CHECKSUM完全相同.

这是我发布的完整结果的帖子:http: //networkprogramming.wordpress.com/2011/01/14/binary_checksum-vs-hashbytes-in-sql/

  • 这并不能回答问题。 (2认同)

小智 5

我发现校验和冲突(即,两个不同的值返回相同的校验和)比大多数人似乎更常见。我们有一个货币表,使用ISO货币代码作为PK。在少于200行的表中,有三对货币代码返回相同的Binary_Checksum():

  • “ ETB”和“ EUR”(埃塞俄比亚比尔和欧元)都返回16386。
  • “ LTL”和“ MDL”(立陶宛立特和摩尔多瓦列伊)均返回18700。
  • “ TJS”和“ UZS”(索莫尼人和乌兹别克斯坦索姆人)都返回20723。

ISO文化代码也是如此:“ de”和“ eu”(德语和巴斯克语)都返回1573。

在这些情况下,将Binary_Checksum()更改为Checksum()可以解决问题……但在其他情况下,可能无济于事。因此,我的建议是在过分依赖这些功能的唯一性之前进行彻底的测试。


Yas*_*sir 5

使用 CHECSUM 时要小心,你可能会得到意想不到的结果。以下语句产生相同的校验和值;

SELECT CHECKSUM (N'??????????iPhone?????', 5, 4102)
SELECT CHECKSUM (N'PlayStation Now – Sony startet Spiele-Streaming im Sommer 2014', 238, 13096)
Run Code Online (Sandbox Code Playgroud)