7

OLE 变体,在旧版本的 Visual Basic 中使用并且在 COM 自动化中普遍使用,可以存储许多不同的类型:整数和浮点数等基本类型,字符串和数组等更复杂的类型,一直到IDispatch实现和指针变体的形式ByRef

变体也是弱类型的:它们将值转换为另一种类型而不会发出警告,具体取决于您应用的运算符以及传递给运算符的值的当前类型。例如,比较两个变体,一个包含整数1,另一个包含字符串"1",是否相等将返回True

因此,假设我正在处理底层数据级别的变体(例如VARIANT在 C++ 或TVarDataDelphi 中 - 即不同可能值的大联合),我应该如何一致地散列变体以使它们遵守正确的规则?

规则:

  • 散列不相等的变体应该在排序和直接相等方面比较为不相等
  • 对于排序和直接相等比较为相等的变体应该哈希为相等

如果我必须使用不同的排序和直接比较规则以使散列适合,那也没关系。

我目前的工作方式是将变体规范化为字符串(如果它们适合),并将它们视为字符串,否则我正在处理变体数据,就好像它是一个不透明的 blob,并对其进行散列和比较原始字节。当然,这有一些限制:数字1..10排序[1, 10, 2, ... 9]等。这有点烦人,但它是一致的,而且工作量很小。但是,我确实想知道这个问题是否有公认的做法。

4

3 回答 3

2

您的问题在使用散列函数和规定的要求之间存在内在张力,这些要求是针对散列的输入进行验证的。我建议我们记住散列的一些一般属性:在散列过程中信息丢失,并且散列冲突是可以预料的。可以构造一个没有冲突的完美哈希,但是如果函数的域是任何可能的 OLE 变体,那么构造一个完美的哈希函数就会有问题(或不可能?)。另一方面,如果我们不是在谈论完美的哈希,那么您的第一条规则就被违反了。

我不知道您要完成的工作的更大背景,但我必须推翻您的一个假设:哈希函数真的是您想要的吗?如果您开发的系统对所有可能的 OLE Variant 属性进行编码而不是散列,以便以后可以调用它们并与其他 Variant 图像进行比较,那么您的要求可以以相当简单的方式得到满足。

您将 Variant 转换为字符串表示的基线实现正在朝这个方向发展。毫无疑问,Variant 可以包含指针、双指针和数组,因此您必须为这些数据类型开发一致的字符串表示。我质疑这种方法是否真的可以归类为哈希。你不只是持久化数据属性吗?

于 2010-03-22T00:35:41.910 回答
0

因此,总而言之,要使内容具有可比性,您首先要以通用格式、字符串或 blob 流式传输。

您如何处理例如本地化,例如实数的形成?与在另一个语言环境中创建的包含相同实数的字符串相比,实数将失败。或具有不同精度设置的真实写入字符串。

在我看来,equal() 的定义是问题,而不是散列。如果“相等”的值可以以不同的方式序列化为字符串(或 blob),则散列将失败。

于 2010-03-20T15:33:37.087 回答
0

相等的 VARIANTS 的哈希码应该相等。

如果不知道用于测试相等性的相等和强制规则,就很难提出适当的实现。

于 2010-03-21T17:09:44.513 回答