数学建模-python递归、lingo解多元一次方程

在了解如何用python、lingo解多元一次方程问题之前我们先了解什么是递归,因为python解多元一次方程问题是递归算法的一个经典算法习题,也是python解多元一次方程问题用到的主要算法。

简单说程序调用自身的编程技巧叫递归。递归的思想是把一个大型复杂问题层层转化为一个与原问题规模更小的问题,问题被拆解成子问题后,递归调用继续进行,直到子问题无需进一步递归就可以解决的地步为止。

递归算法主要的难点:

1、如何将原问题转化为一个与原问题规模更小的问题。

2、递归的终止条件。

目录

问题描述:

目标描述:

算法思路:

代码实现:

按照上述思路python实现如下:

lingo实现如下:


问题描述:

目标描述:

 求解多元一次方程,列出这些解,并统计解的个数。

原问题可以看做为:

的形式

算法思路:

从静态上看,单个\,x_{i}的取值范围为\left [ 0, \frac{s}{a_{i}}\right]

从动态上看,已决定的x_{i}对未决定的x_{i}的范围有影响。

例如,在已经决定x_{}_{1}的情况下,x_{2}的上限从 \frac{s}{a_{1}}变为\frac{s-a_{1}x_{1}}{a_{2}}

问题的规模分布在两个维度上:

  • 变量的个数
  • 总和S 

一个成功的递归算法势必要以某种方式或方程的某种内在联系缩减需要考虑的变量个数以及总和S。

可以将方程的解分为两组:

  • x_{n}= 0,此时相当于解为s= \sum_{i= 1}^{n-1}a_{i}x_{i}
  • x_{n}\geqslant 1,此时相当于解为s-a_{n}= \sum_{i=1}^{n}a_{i}x_{i}

 这种划分方式就是根据各方程之间的内在联系来进行划分,且产生的子问题分别在变量个数与总和上比原问题小。

递归下去到最底层就会触及到边界条件,边界条件为:

这种划分是不重复、无遗漏的,且产生的子问题分别在变量个数与总和上比原问题小。分解不断进行下去就会触及边界,边界条件是:

  • n=0,不是方程的解。
  • s<0,不是方程的解。
  • s=0,是方程的解。

代码实现:

按照上述思路python实现如下:

def solve(val, data):
    def solution(val, data):
        if len(data) == 0:
            return
        elif val < 0:
            return
        elif val == 0:
            xs.append(tuple(x))
            return
        else:
            solution(val, data[:-1])  # 减小变量个数
            x[len(data) - 1] += 1
            solution(val - data[-1], data)  # 减小val
            x[len(data) - 1] -= 1
            return

    x = [0] * len(data)
    xs = []
    solution(val, data)
    return xs,len(xs)


data = [57,71,87,97,99,101,103,113,114,115,128,129,131,137,147,156,163,186]
print(solve(1000,data))

lingo实现如下:

 因为lingo软件本身的限制,所以使用lingo进行求解,只能求出众多可行解中的一个可行解。

评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

!continue!

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值