3

我需要将此 c# 函数转换为 T-SQL UDF

我需要从数据库中获取嗡嗡声距离小于 x 的所有行。这个函数只是解决方案的一部分。

csharp 函数为这 2 个哈希返回 40,而 t-sql 函数返回 52

14714557628763197901

15383788748848265778

public static ulong csharp_hamming_distance(ulong hash1, ulong hash2)
{
ulong x = hash1 ^ hash2;
const ulong m1 = 0x5555555555555555UL;
const ulong m2 = 0x3333333333333333UL;
const ulong h01 = 0x0101010101010101UL;
ulong m4 = 0x0f0f0f0f0f0f0f0fUL;
x -= (x >> 1) & m1;
x = (x & m2) + ((x >> 2) & m2);
x = (x + (x >> 4)) & m4;
return (x * h01) >> 56;
}

我有样品,但它没有给我相同的结果。

create function HammingDistance1(@value1 char(8000), @value2 char(8000))
returns int
as
begin
    declare @distance int
    declare @i int
    declare @len int

    select @distance = 0,
           @i =1,
           @len = case when len(@value1) > len(@value2)
                       then len(@value1)
                       else len(@value2) end

    if (@value1 is null) or (@value2 is null)
        return null

    while (@i <= @len)
        select @distance = @distance +
                           case 
                           when substring(@value1,@i,1) = substring(@value2,@i,1)
                                then 0
                           when substring(@value1,@i,1) < substring(@value2,@i,1)
                                then  CAST(substring(@value2,@i,1) as smallint) -  CAST(substring(@value1,@i,1) as smallint)
                           when substring(@value1,@i,1) > substring(@value2,@i,1)
                                then  CAST(substring(@value1,@i,1) as smallint) - CAST(substring(@value2,@i,1) as smallint)
                          else 1 end,
               @i = @i +1
    return @distance
end 

任何帮助将不胜感激

4

1 回答 1

1

在汉明计算中,整数被视为位。汉明距离是比特差的数量,可以计算为两个值的异或中非零比特的数量。对于您提供的两个整数,按位汉明距离确实是 40。

14714557628763197901=
   1100110000110100100111000011001111001001011100011101000111001101

15383788748848265778=
   1101010101111110001100100101110000111010110000000111101000110010

^= 0001100101001010101011100110111111110011101100011010101111111111

这是 40 个非零位。显示的 C# 只是计算它们的一种奇特方式。

字符串不是这种情况。在 TSQL 中,您正在执行字符串汉明,这通常只是字符不同的位置数。对这两个值作为字符串执行经典的汉明距离给出:

"14714557628763197901"
"15383788748848265778"
 01111111110111111111 = 18

您的示例 TSQL 代码正在执行修改后的汉明计算;要获得经典的汉明距离,只需删除最后两个when子句。

在 TSQL 中执行二进制汉明距离bigint将非常困难,因为 TSQL 不支持对 bigint 的按位运算。但是,您可以使用整数运算分别对左右两半执行计算,然后将它们相加。唯一棘手的部分是该死的 MSB 和对换档的影响。

对小数执行汉明距离没有明确定义。您需要更具体地说明您认为这意味着什么。

于 2014-02-17T11:09:22.607 回答