Matlab+Yalmip求解速度变慢的解决过程

本文记录了在Matlab中使用Yalmip解决整数规划问题时遇到的性能瓶颈,尤其是在大量循环中。通过分析发现Yalmip中变量累积导致的内存消耗,作者分享了变量定义位置调整和yalmip('clear')技巧,成功解决了计算时间线性增长的问题,提升了解决效率。
摘要由CSDN通过智能技术生成

Matlab+Yalmip求解速度变慢的解决过程记录

Matlab+Yalmip+其他的求解器是在Matlab中解决各种优化问题的常见方式。但是,在最近的一个项目中,我遇到了一个问题。此项目中,代码主要是一个循环,然后在每个循环中都需要求解若干个规模不变的整数规划问题。每次定义的变量都有相同的变量名,在Matlab工作区中会覆盖之前的变量,因此随着循环的运行,工作区中的变量数并不会增加。整个代码的过程大概如下:

for
define variables
define constraints
solve
end

由于这些整数规划问题的规模并不大,所以在最开始的时候,求解器可以在非常快的速度内进行求解。例如,每个循环求解20次整数规划问题,每次所需要的时间不超过1s,因此,一个循环最开始所需的时间在20s之内。然而,随着迭代的逐渐进行,我发现每个循环所需要的计算时间逐渐增加。到了最后,一次循环需要花费我大概700s的时间。100次循环,一共需要消耗10h的时间,这个时间显然是不可接受的。可以从下图中看到,每次循环的计算时间,随着循环的次数基本呈线性增加。

pic

最开始,我以为是求解器的问题,但是我试用了三种求解器:Cplex,Gurobi,以及Matlab自带的Intlinprog工具箱,发现都会出现同样的状况。最后我检查了求解后的result,发现在迭代后期,每次求解的solvertime只需要0.068s,然而yalmiptime需要20.3917s!显然,问题是出在了Yalmip上。

pic2

在反复百度和Google后,我都没有找到解决方案。最终,我直接去Github去询问了Yalmip的作者Johan大神,然后他给我的回复如下:

image-20210729191750989

即,虽然我每次在for循环中定义的变量的名称是相同的,看似在matlab中,定义名称相同的变量会覆盖原变量。但是,在Yalmip中,原有的变量并不会被删除,而新的变量会被源源不断地创建,这会导致变量数越来越多。因此,作者给了我两种方法:

  • 方法一:将变量的定义放在循环外面,即:

    define variables
    define constraints
    for
    add stuff that changes
    solve
    end
    
  • 方法二:在定义变量前使用yalmip(‘clear’),即:

    for
    yalmip('clear')
    define variables
    define constraints
    solve
    end
    

最终,我使用了方法2,然后解决了上述的问题。从下图可以看到,即使运行了750次循环,大部分循环所需的时间都在10s左右,只有少部分需要30s的时间,该问题被成功解决。

image-20210729192106167

最后,我特别想要对Yalmip的作者Johan表示一个respect!
(Github讨论区的回复链接:https://github.com/yalmip/YALMIP/discussions/956非常巧的是,在Yalmip的Google Group中,有人在几乎同一时间提了一个和本文一模一样的问题,链接为:https://groups.google.com/g/yalmip/c/DJ5j0CeHbEI)

评论 10
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值