【问题标题】:Python multiplicative inverse in GF(2) finite fieldGF(2)有限域中的Python乘法逆
【发布时间】:2013-06-29 18:07:59
【问题描述】:

这两个函数执行扩展欧几里得算法,然后找到乘法逆。订单似乎是正确的,但它并没有按照我对悉尼大学http://magma.maths.usyd.edu.au/calc/ 的这个工具的期望回来,因为这是在 GF(2) 有限域中完成的,我想我错过了一些关键步骤从基数 10 转换为该字段。

这是在以 10 为底的基础上进行测试和工作的,但在这里可能无法采用具有二进制系数的多项式。所以我的问题是我错误地将 Python 的哪些部分应用到这个算法中,例如 // floor,这可能不是函数在 base 10 中能够在 GF(2) 中做到这一点的能力。

上面的工具可以这样测试:

R<x>:=PolynomialRing(GF(2));
p:=x^13+x+1; q:=x^12+x;
g,r,s:=XGCD(p,q);

g eq r*p+s*q;

g,r,s;

功能:

def extendedEuclideanGF2(self,a,b): # extended euclidean. a,b are values 10110011... in integer form
    inita,initb=a,b;  x,prevx=0,1;  y,prevy = 1,0
    while b != 0:
        q = int("{0:b}".format(a//b),2)
        a,b = b,int("{0:b}".format(a%b),2);
        x,prevx = (int("{0:b}".format(prevx-q*x)), int("{0:b}".format(x,2)));  y,prevy=(prevy-q*y, y)
    print("Euclidean  %d * %d + %d * %d = %d" % (inita,prevx,initb,prevy,a))
    return a,prevx,prevy  # returns gcd of (a,b), and factors s and t

def modular_inverse(self,a,mod): # a,mod are integer values of 101010111... form
    a,mod = prepBinary(a,mod)
    bitsa = int("{0:b}".format(a),2); bitsb = int("{0:b}".format(mod),2)
    #return bitsa,bitsb,type(bitsa),type(bitsb),a,mod,type(a),type(mod)
    gcd,s,t = extendedEuclideanGF2(a,mod); s = int("{0:b}".format(s))
    initmi = s%mod; mi = int("{0:b}".format(initmi))
    print ("M Inverse %d * %d mod %d = 1"%(a,initmi,mod))
    if gcd !=1: return mi,False
    return mi   # returns modular inverse of a,mod

我一直在用这样的多项式进行测试,但当然是二进制形式:

p = "x**13 + x**1 + x**0" 
q = "x**12 + x**1"

【问题讨论】:

  • 您是否还可以显示一些函数的定义,例如prepBinary?

标签: python python-2.7 polynomial-math finite-field galois-field


【解决方案1】:

该函数在使用 base-10 测试时有效,因为您的所有转换 int("{0:b}".format(x)) 对 x 没有影响:

37 == int("{0:b}".format(37), 2)  # >>> True

python 中的 Number 对象都是以 10 为底的。将您的数字转换为二进制字符串,然后再转换回整数无效。这是您的函数的替代版本,它应该在 ab 作为 base-10 整数并以二进制形式返回它们。您可以删除 bin() 函数以返回以 10 为基数的数字,或者使用类似 lambda x: int("%d".format(x)) 的东西在函数的第一行将 ab 从二进制转换为十进制。

def extendedEuclideanGF2(a, b): # extended euclidean. a,b are values 10110011... in         integer form
    inita, initb = a, b   # if a and b are given as base-10 ints
    x, prevx = 0, 1
    y, prevy = 1, 0
    while b != 0:
        q = a//b
        a, b = b, a%b
        x, prevx = prevx - q*x, x
        y, prevy = prevy - q*y, y
    print("Euclidean  %d * %d + %d * %d = %d" % (inita, prevx, initb, prevy, a))
    i2b = lambda n: int("{0:b}".format(n))  # convert decimal number to a binary value in a decimal number
    return i2b(a), i2b(prevx), i2b(prevy)  # returns gcd of (a,b), and factors s and t

说了这么多,不要在这样的函数中使用 lambdas - 我建议编写程序以避免完全使用二进制文件,您可以通过仅在程序与源代码的接口处从/转换为二进制文件来做到这一点数据。

【讨论】:

  • 谢谢。我正在尝试在有限域内的除法中使用它。不确定这是否正确,但 return self * (mi % min(other,self)) % min(other,self) 其中 mi 是 self 和 other 的 mod_inverse。你怎么看?
  • 我看到了真正的问题:GF2 中的算术规则与整数规则相同。 Python 中的运算符不遵循 GF2 算术 - 它们执行进位操作。您可以通过编写 GF2 类使它们表现得像 GF2,但如果您尝试在 GF2 中执行除法,那么在GF2 类。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-09-06
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多