Karatsuba算法:分裂字符串

时间:2014-11-07 19:18:47

标签: c algorithm biginteger karatsuba

我正在尝试用C语言实现Karatsuba算法。 我使用char字符串(它是某个基数中的数字),虽然我认为我已经理解了大多数Karatsuba算法,但我没有得到我应该将字符串分成多个的位置。

例如,我应该在哪里切割 123 * 123 ,我应该在哪里切割 123 * 12
我无法找到适用于这两种计算的解决方案。

我尝试将它切成两半并将结果放在地板上,如果数字是奇数,但它不起作用,并且天花板也不起作用。

有任何线索吗?

设a,b,c和d为字符串的一部分。

  • 让我们试试123 * 12

    首先尝试(a = 1,b = 23,c = 1,d = 2)(失败)

    z0 = a * c = 1
    z1 = b * d = 46
    z2 = (a + b) * (c + d) - z0 - z1 = 24 * 3 - 1 - 46 = 72 - 1 - 46 = 25
    
    z0_padded = 100
    z2_padded = 250
    
    z0_padded + z1 + z2_padded = 100 + 46 + 250 = 396 != 123 * 12
    

    第二次尝试(a = 12,b = 3,c = 12,d = 0)(失败)

    z0 = 144
    z1 = 0
    z2 = 15 * 12 - z1 - z0 = 180 - 144 = 36
    
    z0_padded = 14400
    z2_padded = 360
    
    z0_padded + z1 + z2_padded = 14760 != 1476
    

    第三次尝试(a = 12,b = 3,c = 0,d = 12)(成功)

    z0 = 0
    z1 = 36
    z2 = 15 * 12 - z0 - z1 = 144
    
    z0_padded = 0
    z2_padded = 1440
    
    z0_padded + z1 + z2_padded = 1476 == 1476
    
  • 让我们试试123 * 123

    首先尝试(a = 1,b = 23,c = 1,d = 23)(失败)

    z0 = 1
    z1 = 23 * 23 = 529
    z2 = 24 * 24 - z0 - z1 = 46
    
    z0_padded = 100
    z2_padded = 460
    
    z0_padded + z1 + z2_padded = 561 != 15129
    

    第二次尝试(a = 12,b = 3,c = 12,d = 3)(成功)

    z0 = 12 * 12 = 144
    z1 = 3 * 3 = 9
    z2 = 15 * 15 - z0 - z1 = 72
    
    z0_padded = 14400
    z2_padded = 720
    
    z0_padded + z1 + z2_padded = 15129 == 15129
    

    第三次尝试(a = 12,b = 3,c = 1,d = 23)(失败)

    z0 = 12
    z1 = 3 * 23 = 69
    z2 = 15 * 24 - z0 - z1 = 279
    
    z0_padded = 1200
    z2_padded = 2799
    
    z0_padded + z1 = z2_padded = 4068 != 15129
    

在这里,我没有得到我搞砸了的地方。请注意,我的填充方法在数字末尾添加 n 零,其中 n = m * 2 m 等于最长字符串的大小除以二。

修改

既然我已经理解bd必须具有相同的长度,它几乎每次都有效,但仍然有例外:例如 1234 * 12

a = 123
b = 4
c = 1
d = 2

z0 = 123
z1 = 8
z2 = 127 * 3 - 123 - 8 = 250

z0_padded = 1230000
z2_padded = 25000

z0_padded + z1 + z2_padded = 1255008 != 14808

这里,假设我正确地分割了字符串,问题是填充,但我不知道应该如何填充。我在Wikipedia上读到我应该根据最大字符串的大小来填充(参见几行),应该有另一个解决方案。

1 个答案:

答案 0 :(得分:2)

Karatsuba算法是一种很好的执行乘法的方法 如果您希望它起作用,bd必须具有相同的长度。

以下是计算123x12的两种可能性:

a= 1;b=23;c=0;d=12;
a=12;b= 3;c=1;d= 2;

让我们解释它如何适用于第二种情况:

123=12×10+3
 12= 1×10+2
123×12=(12×10+3)×(1×10+2)
123×12=12×1×100+             (12×2+3×1)×10+3×2
123×12=12×1×100+((12+3)×(1+2)-12×1-3×2)×10+3×2

让我们解释它对第一种情况的作用:

123=1×100+23
 12=0×100+12
123×12=(1×100+23)×(0×100+12)
123×12=1×0×10000+              (1×12+23×0)×100+23×12
123×12=1×0×10000+((1+23)×(0+12)-1×0-23×12)×100+23×12

它也适用于10^k2^kn,而不是10100