列生成算法(求解Cutting Stock问题)
列生成是用于求解大规模线性优化问题的一种算法,其实就是单纯形法的一种形式。单纯性可以通过不断迭代,通过换基变量的操作,最终找到问题的最优解。但是当问题的规模很大之后,变量的个数就会增大到在有限时间内无法有效迭代求解。所以可以用列生成方法求解,列生成方法可以一开始不列举所有的列,通过不断给模型中加入列的方式,最终找到全部解,其关键点就是加新列的过程,可以只加入能让目标值更优的列,从而减少变量的使用个数。
列生成算法流程
列生成过程中,需要将问题建模为主问题+子问题的形式。
主问题:就是原问题,主要用于决策是否选用某些方案(列)
主问题松弛问题:将主问题变量范围正整数松弛到正数
限制主问题:主问题去掉一部分列
限制主问题对偶问题:对限制主问题求对偶
价格子问题:原问题的局部问题,用于生成新的方案(列)
求解Cutting Stock问题
问题描述:
将一些钢管切割成为需要的长度以满足客户需求,要求使用的钢管最少。
每根钢管长度L=16m
需求:3m钢管25根;6m钢管20根,7米钢管18根
模型建立
主问题
s.t.\qquad\qquad\qquad\qquad\qquad\\
\sum_{j \in J} x_j a_{ij} \ge d_i \qquad \forall i \in I\\
x_j \in Z \qquad \qquad \quad \forall j \in J \]
\(x_j\): 方案选用的个数
\(a_{ij}\): 方案\(j\)中钢管\(i\)的个数
\(d_i\): 钢管\(i\)的需求量
主问题松弛问题
s.t.\qquad\qquad\qquad\qquad\qquad\\
\sum_{j \in J} x_j a_{ij} \ge d_i \qquad \forall i \in I\\
x_j \ge 0 \qquad \qquad \quad \forall j \in J \]
变量是整数的情况下无法用列生成法求得最优解,需要将问题松弛。如果需要求得整数最优解需要结合分支定界算法。
限制主问题
s.t.\qquad\qquad\qquad\qquad\qquad\\
\sum_{j \in J} x_j a_{ij} \ge d_i \qquad \forall i \in I\\
x_j \ge 0 \qquad \qquad \quad \forall j \in \Omega_j \]
将主问题中的变量规模减小,一开始只加入一部分可行的切割方案(\(a_j\),列),列生成就是不断生成新的\(a_j\) 加入到问题中。判断一个列是否可以加入到问题,需要判断检验数\(\sigma_j = c_j - c_B B^{-1}a_j\),如果检验数为负,就可以将新的列加入。其中\(c_BB^{-1}\)有两重含义:
- 通过限制主问题求得的影子价格
- 通过限制主问题求得的对偶变量
对偶问题和原问题有同样的最优解,将原问题进行对偶,可以把原问题的变量转化为约束、约束转化为变量,因此,对于变量很多的问题将其转化为对偶问题可以很容易得到其子问题。
对偶问题
s.t.\qquad\qquad\qquad\qquad\qquad\\
\sum_{i in \ I} a_{ij} v_i \le 1 \qquad \qquad \forall j \in \Omega_j \\
v_j \ge 0 \qquad \qquad \qquad \quad
\forall i \in I \]
对偶问题用于推导子问题。可以进入主问题的列,就是检验数为负数的列,对于对偶问题,就是违反了约束的列。对偶问题中只有一个约束,\(\sum_{i in \ I} a_{ij} \lambda_i \le 1\)可以写成\(1-\sum_{i \in I} a_i \lambda_i \ge 0\),求其最小值,如果最小值小于0,则说明其违反了约束。子问题用于生成新的切割方案(列),子问题的约束对应切割约束。
子问题
s.t.\qquad\qquad\qquad\qquad\qquad\\
\sum_{i \in I} a_i l_i \le L \qquad \forall i \in I \\
a_i \ge 0 \qquad \quad \quad \forall i \in I \]
数据带入模型
以下所有的求解都可以用CPLEX进行求解,直接用CPLEX IDE实现
1. 启发式获得初始切割方案
首先有可行的切割方案才能构造出主问题,因此可以用启发式先计算出一些可行的切割方案,用于构造主问题。很简单的,每根钢管只生产一种产品,可以得到三种切割方案
切割方案 | 3m | 6m | 7m |
---|---|---|---|
1 | 5 | 0 | 0 |
2 | 0 | 2 | 0 |
3 | 0 | 0 | 2 |
2.开始列生成迭代
第1次迭代
松弛限制主问题:
s.t.\qquad\qquad\qquad\qquad\qquad\\
\quad\quad\quad5x_1 \qquad \qquad \quad \ge 25 \\
\quad\quad\quad\qquad 2x_2 \qquad \quad \ge 20 \\
\quad\quad\quad\qquad \qquad 2x_3 \quad\ge 18 \\
\quad\quad\quad x_1,\quad x_2,\quad x_3 \quad \ge 0 \]
对偶问题:
s.t.\qquad\qquad\qquad\qquad\qquad\\
\qquad \quad 5v_1 \qquad \qquad \qquad \quad\le 1 \\
\qquad \quad\qquad \quad 2v_2 \qquad \quad \quad\le 1 \\
\qquad \quad\qquad \qquad \qquad 2v_3\quad \le 1 \\
\quad\quad \quad v_1,\quad \quad v_2,\quad \quad v_3 \quad \ge 0 \]
求得对偶变量的值,将其带入到子问题中
子问题:
s.t.\qquad\qquad\qquad\qquad\qquad\\
\quad\quad\quad 3a_1+6a_2+7a_3 \le 16\\
\quad\quad\quad a_1, \quad a_2, \quad a_3 \quad \ge 0 \]
目标函数值为-0.2<0,可以加入到主问题中继续求解,新加入的一列是\(a_4=[1,2,0]^T\),表示这个方案中一根钢管切出一根3m和2根6米
第2次迭代
松弛限制主问题:
s.t.\qquad\qquad\qquad\qquad\qquad\\
\quad\quad\quad5x_1 \qquad \qquad \quad + x_4 \quad\ge 25 \\
\quad\quad\quad\qquad 2x_2 \qquad \quad + 2x_4 \ge 20 \\
\quad\quad\quad\qquad \qquad 2x_3 \quad \quad\quad\quad\ge 18 \\
\quad\quad\quad x_1,\quad x_2,\quad x_3, \quad x_4 \quad \ge 0 \]
对偶问题:
s.t.\qquad\qquad\qquad\qquad\qquad\\
\qquad \quad 5v_1 \qquad \qquad \qquad \quad\le 1 \\
\qquad \quad\qquad \quad 2v_2 \qquad \quad \quad\le 1 \\
\qquad \quad\qquad \qquad \qquad 2v_3\quad \le 1 \\
\qquad \quad v_1\quad+2v_2 \quad\quad\quad\quad\le 1 \\
\quad\quad \quad v_1, \qquad v_2, \qquad v_3 \quad \ge 0 \]
求得对偶变量的值,将其带入到子问题中
子问题:
s.t.\qquad\qquad\qquad\qquad\qquad\\
\quad\quad\quad 3a_1+6a_2+7a_3 \le 16\\
\quad\quad\quad a_1, \quad a_2, \quad a_3 \quad \ge 0 \]
目标函数值为-0.1<0,可以加入到主问题中继续求解,可以加入到主问题中继续求解,新加入的一列是\(a_4=[1,1,1]^T\),表示这个方案中一根钢管切出1根3m,1根6米,1根7米
第3次迭代
松弛限制主问题:
s.t.\qquad\qquad\qquad\qquad\qquad\\
\quad\quad\quad5x_1 \qquad \qquad \quad + x_4 \quad + x_5\ge 25 \\
\quad\quad\quad\qquad 2x_2 \qquad \quad + 2x_4 +x_5\ge 20 \\
\quad\quad\quad\qquad \qquad 2x_3 \quad \quad\quad\quad +x_5\ge 18 \\
\quad\quad x_1,\quad x_2,\quad x_3, \quad x_4, \quad x_5 \quad\quad\ge 0 \]
对偶问题:
s.t.\qquad\qquad\qquad\qquad\qquad\\
\qquad \quad 5v_1 \qquad \qquad \qquad \quad\le 1 \\
\qquad \quad\qquad \quad 2v_2 \qquad \quad \quad\le 1 \\
\qquad \quad\qquad \qquad \qquad 2v_3\quad \le 1 \\
\qquad \quad v_1\quad+2v_2 \quad\quad\quad\quad\le 1 \\
\qquad \quad v_1\quad+v_2\quad+v_3 \quad\le 1 \\
\quad\quad \quad v_1, \qquad v_2, \qquad v_3 \quad \ge 0 \]
求得对偶变量的值,将其带入到子问题中
子问题:
s.t.\qquad\qquad\qquad\qquad\qquad\\
\quad\quad\quad 3a_1+6a_2+7a_3 \le 16\\
\quad\quad\quad a_1, \quad a_2, \quad a_3 \quad \ge 0 \]
根据求解可以得到
目标值:20.2
切割方案:方案1选择1.2个;方案4选择1个,方案5选择18个
最后求得的结果包含了小数,如果想要取得整数解,需要结合分支定界算法
列生成算法(求解Cutting Stock问题)的更多相关文章
- excel的列生成算法
echo '<pre>'; $i = 1; while($i < 703){ $char1 = floor($i / 26); $char2 = $i % 26; if($i % 2 ...
- 干货 | 10分钟带你彻底了解column generation(列生成)算法的原理附java代码
OUTLINE 前言 预备知识预警 什么是column generation 相关概念科普 Cutting Stock Problem CG求解Cutting Stock Problem 列生成代码 ...
- 二维剪板机下料问题(2-D Guillotine Cutting Stock Problem) 的混合整数规划精确求解——数学规划的计算智能特征
二维剪板机下料问题(2-D Guillotine Cutting Stock Problem) 的混合整数规划精确求解——数学规划的计算智能特征 二维剪板机下料(2D-GCSP) 的混合整数规划是最优 ...
- [2017BUAA软工]第一次个人项目 数独的生成与求解
零.Github链接 https://github.com/xxr5566833/sudo 一.PSP表格 PSP2.1 Personal Software Process Stages 预估耗时(分 ...
- 跳跃的舞者,舞蹈链(Dancing Links)算法——求解精确覆盖问题
精确覆盖问题的定义:给定一个由0-1组成的矩阵,是否能找到一个行的集合,使得集合中每一列都恰好包含一个1 例如:如下的矩阵 就包含了这样一个集合(第1.4.5行) 如何利用给定的矩阵求出相应的行的集合 ...
- 一个UUID生成算法的C语言实现 --- WIN32版本 .
一个UUID生成算法的C语言实现——WIN32版本 cheungmine 2007-9-16 根据定义,UUID(Universally Unique IDentifier,也称GUID)在时 ...
- 基于粒子群算法求解求解TSP问题(JAVA)
一.TSP问题 TSP问题(Travelling Salesman Problem)即旅行商问题,又译为旅行推销员问题.货郎担问题,是数学领域中著名问题之一.假设有一个旅行商人要拜访n个城市,他必须选 ...
- EM 算法求解高斯混合模型python实现
注:本文是对<统计学习方法>EM算法的一个简单总结. 1. 什么是EM算法? 引用书上的话: 概率模型有时既含有观测变量,又含有隐变量或者潜在变量.如果概率模型的变量都是观测变量,可以直接 ...
- 算法实践——舞蹈链(Dancing Links)算法求解数独
在“跳跃的舞者,舞蹈链(Dancing Links)算法——求解精确覆盖问题”一文中介绍了舞蹈链(Dancing Links)算法求解精确覆盖问题. 本文介绍该算法的实际运用,利用舞蹈链(Dancin ...
随机推荐
- 题解 [NOI2019]弹跳
题目传送门 题目大意 给出 \(n\) 做城市,每座城市都有横纵坐标 \(x,y\).现在给出 \(m\) 个限制 \(p,t,l,r,d,u\),表示从 \(p\) 城市出发,可以花费 \(t\) ...
- OutOfMemoryException异常解析
一.概述 在国庆休假快结束的最后一天晚上接到了部门老大的电话,某省的服务会出现崩溃问题.需要赶紧修复,没错这次的主角依旧是上次的"远古项目"没有办法同事都在休假没有人能帮忙开电脑远 ...
- Visual Studio 重置窗口布局
Visual Studio 重置窗口布局
- Java:泛型小记
Java:泛型小记 对 Java 中的 泛型类,做一个微不足道的小小小小记 泛型实现 概述 开篇: List<String> l1 = new ArrayList<String> ...
- k8s replicaset controller 分析(3)-expectations 机制分析
replicaset controller分析 replicaset controller简介 replicaset controller是kube-controller-manager组件中众多控制 ...
- 移动端 h5 uniapp 读,写,删本地文件或sd文件
移动端 h5 uniapp 读,写,删本地文件或sd文件 应用场景: 当我们需要做离线应用或者是加载本地文件时使用到此方法.(本篇文章给大家分享访问app私有文件目录,系统公共目录,sd外置存储的文件 ...
- Vue el 使用el-checkbox-group复选框进行单选框操作
el-checkbox-group这个组件与其他复选框不一样,我当初也是半天不知道怎么操作 页面使用v-model绑定 size就是等比例缩小放大,v-ror循环应该看的懂.重要的是@chage到我们 ...
- mipi csi接口,1条lane支持多少像素,200w像素需要几条lane,为什么,怎么计算出来的?谢谢!
按帧频FRAME=60HZ, 分辨率480*800来计算;以WVGA 显示分辨率,24BIT图片,60幁为例,在理想状态下(未包含RGB信号前后肩宽度),总传输速率最小为:480*800*8BIT*3 ...
- STM32直流电机启动(一)驱动电路的介绍
驱动电路 典型的H桥驱动电路如下:要使电机旋转只需导通对角线上的两个三极管即可,如导通Q1,Q4,关闭Q2,Q4即可驱动电机正转:若想电机反向转动,即导通三极管Q2,Q3,关闭Q1,Q4.此时电路图可 ...
- Linux C语言链表你学会了吗?
链表是一种常见的基础数据结构,结构体指针在这里得到了充分的利用.链表可以动态的进行存储分配,也就是说,链表是一个功能极为强大的数组,他可以在节点中定义多种数据类型,还可以根据需要随意增添,删除,插入节 ...