扩展欧几里得算法求多项式的乘法逆元

首先,算法如下:

当r=0时,w即为多项式的乘法逆元。

为了帮助进一步理解,这里是实例:

因此我们只需要输入多项式a,b,然后利用循环求得q,r,v,w就可以,可以看到计算过程需要用到模运算的多项式加减、乘、除、取余运算,实现步骤如下

最后,只剩下编程实现了,因为字符串很方便操作,因此我用字符串实现,实现过程如下:


#求多项式的商 poly_div函数
def poly_div(a,b,ans):
        l=len(a)-len(b)
        ans+='1'
        r = ''
        for i in range(0, len(b)):
            if a[i] == b[i]:
                r += '0'
            else:
                r += '1'
        for i in range(len(b), len(a)):
            r += a[i]
        r = r.lstrip('0')  # 去除前导零
        if len(r)>=len(b):
            for i in range(l-len(r)+len(b)-1):
                ans+='0'
            return poly_div2(r,b,ans)
        elif r==b :
            for i in range(l-1):
                ans+='0'
            ans+='1'
            return ans
        else:
            for i in range(l):
                ans+='0'
            return ans
def poly_div(a,b):
    ans=''#用来存商,因为递归调用需要三参数,因此设计了poly_div函数嵌套调用poly_div2
    return poly_div2(a,b,ans)
#求多项式余数,模运算----实质是求余数
def mod(a,b):
    l = len(a) - len(b)
    r = ''
    for i in range(0, len(b)):
        if a[i] == b[i]:
            r += '0'
        else:
            r += '1'
    for i in range(len(b), len(a)):
        r += a[i]
    r = r.lstrip('0')  # 去除前导零
    if len(r) >=len(b):
        return mod(r,b)
    else:
        return r
#求两个多项式的最大公约数
def gcd(a,b):
    #a%b,a1111111  b10111
    r=''
    p=len(a)-len(b)
    for i in range(0,len(b)):
        if a[i]==b[i]:
            r+='0'
        else:
            r+='1'
    for i in range(len(b),len(a)):
        r+=a[i]
    r=r.lstrip('0')
    b=b.lstrip('0')
    a=''
    if b!=r:
        if(len(r)>len(b)):
            return  gcd(r,b)
        else:
            return gcd(b,r)
    else:
        return b
#求多项式加减法---实质是抑或运算
def poly_add_sub(a,b):
    if len(b)>len(a):
        a,b=b,a
    r=''
    for i in range(0,len(a)-len(b)):
        r+=a[i]
    for i in range(len(b)):
        if a[i+len(a)-len(b)]==b[i]:
            r+='0'
        else:
            r+='1'
    r.lstrip('0')#去除前导零
    return r
#求乘法
def poly_mul(a,b):
    #拆成右边加零然后相加
    if len(a)<len(b):
        a,b=b,a
    c=a
    r=''
    for i in range(len(b)-1,-1,-1):
        if i!=len(b)-1:
            c=c+'0'
        if b[i]=='1':
            r=poly_add_sub(c,r)
    return r

def poly_inv(a,b):
        v=['1','0']
        w=['0','1']
        r=[a,b]
        q=[]
        i=0
        while r[i+1]!='':
            r.append(mod(r[i],r[i+1]))
            print('r[',i+1,']=',r[i+2])
            q.append(poly_div(r[i],r[i+1]))
            print('q=',q[i])
            v.append(poly_add_sub(v[i],poly_mul(q[i],v[i+1])))
            print('v[', i + 1, ']=', v[i+2])
            w.append(poly_add_sub(w[i],poly_mul(q[i],w[i+1])))
            print('w[', i + 1, ']=', w[i+2])
            i=i+1
            print('----------------------------------------------')
        return w[i]


#这里为了方便调试直接给变量赋值
#a=input("请输出多项式a(x):")
a='100011011'
#b=input("\n输入多项式b(x):")
b='10000011'
ans=poly_inv(a,b)
print('乘法逆元的结果为=',ans)

另外补充一下,多项式求最大公因数可能有点难度,也是利用了辗转相除法实现。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值