关于线性规划问题是什么已经有很多人早就说明过了,我也小抄一波给大家预热预热,线性规划问题是运筹学中研究较早、发展较快、应用广泛、方法较成熟的一个重要分支,它是辅助人们进行科学管理的一种数学方法。

在一定条件下,合理安排人力物力等资源,使经济效果达到最好.一般地,求线性目标函数在线性约束条件下的最大值或最小值的问题,统称为线性规划问题。

满足线性约束条件的解叫做可行解,由所有可行解组成的集合叫做可行域。决策变量、约束条件、目标函数是线性规划的三要素。

OK,进入正题,什么是单纯形算法:

单纯形算法的基本思想是从一个基本可行解出发,进行一系列的基本可行解的变换,其中基本可行解是指在任何约束标准型线性规划问题中,只要将所有非基本变量都置为0,从约束方程式中解出满足约束的基本变量的值,最后得到的解。

单纯形算法的基本步骤是:

  1. 选入基变量,即找到目标函数中的正系数。
  2. 选离基变量,找到约束方程中可以替换的负系数。
  3. 作转轴变换,即将入基变量和离基变量进行替换,然后重新构造单纯形表。
  4. 循环上面三个步骤直到目标函数中所有变量的系数为负值,此时就得到了最优结果。

举例说明:

求解下面这个线性规划模型

首先定义一组基本变量inx[k],和一组非基本变量ninx[v],基本变量就是在中间那三个约束条件里面找的变量,每个约束条件只找一个基本变量,这个基本变量要满足没有在目标函数里面出现并且系数为正,而且找的三个基本变量要不一样,在这个例子就是[x1,x4,x6]。非基本变量就是除了基本变量以外的变量,在这个例子里就是[x2,x3,x5]。

然后定义一个单纯形表Chart[n*m],它的每行基本变量,列是非基本变量,里面的值是目标函数或约束的各个变量的系数,按照本例,则结构如下所示:

/ / x2 x3 x5
/ z=0 -1 3 -2
x1 7 3 -1 2
x4 12 -2 4 0
x6 10 -4 3 8

不过,上面的第一行和第一列实际上是不在Chart里面的,这只是用来提示用的,即,本例子的Chart的尺寸是4*4,而Chart[0,0]的相反数就是解出的值。

好的,既然已经可以有了这个单纯形表,那么之后只要更新这个表就可以了。更新的方法是:

首先,找到入基变量出基变量,所谓入基变量就是将要成为基本变量的非基本变量,而出基变量则是将要脱离基本变量身份而变成非基本变量的基本变量。如何找到这两个变量呢?

对于入基变量,审查z所在的那行,也就是第一行,找到所有值为正的非基本变量,挑一个作为入基变量即可,本例上明显是x3,因为Chart[0,2]=3>0。

对于出基变量,审查入基变量所在的那列,即x3所在那一列,找出所有值为正的那些行,即x4和x6所在行,值分别为4和3,接下来选择min{12/4,10/3}的那行,因为12/4<10/3所以选择x4所在那行,也就是说,x4就是出基变量。

第二步,更新这个单纯形表,更新方法很多啊,不过结果应该都是一样的,我的更新方法是,假设出基变量所在行下标为idy,入基变量所在列下标为idx,则根据这两个来控制Chart表的更新就方便了,首先计算idy那行的值,除了Chart[idy, idx]需要除以Chart[idy,idx]的平方以外,其他几个只需要除以Chart[idy,idx]就行,计算完后立即更新上去。然后更新其他位置,。。。。自己根据例子推一推还是很简单的,我直接放这个例子的第一轮更新的结果, 更新完Chart后就更新基本变量组inx和非基本变量组ninx,把出基变量和入基变量交换就行。

重复上面两个过程,直到目标函数里面的所有系数都不是正值就结束,这样子Chart[0, 0]就是最优目标的值了,我的代码实现用的是Chart[0, 0]的相反数 ,而最优解则是将所有基本变量置为0,然后计算其他非基本变量的值得到的解。

因为这个例子只用在来一轮就能得到最优解,因此下面进一步给出最终结果。

最后放上我的不堪入目的代码(呜呜呜)

#include<iostream>using namespace std;// ct是单纯形表, n是行数, m是列数
double ct[100][100]={0};
int n, m;
// x是所有变量的值
double x[100]={0};
// inx是基本变量的下标,ninx是非基本变量的下标
int inx[100]={0}, ninx[100]={0};void solve(){// 选入基变量double in=ct[0][1];int idx=1;for(int i=2;i<m;i++){if(ct[0][i]>in){in=ct[0][i];idx=i;}}cout<<"入基变量:"<<idx<<","<<in<<",x"<<ninx[idx-1]<<endl;// 选离基变量double out=1e9;int idy = 0;for(int i=1;i<n;i++){if(ct[i][idx]>0){if(1.00*ct[i][0]/ct[i][idx]<out){out=1.00*ct[i][0]/ct[i][idx];idy=i;}}}cout<<"离基变量:"<<idy<<","<<out<<",x"<<inx[idy-1]<<endl;// 计算新的单纯形表// 先更新基本变量表和非基本变量表int t1 = inx[idy-1];inx[idy-1] = ninx[idx-1];ninx[idx-1] = t1;double t = ct[idy][idx];// 其次更新单纯形表中出基变量那一行的值for(int i=0;i<n;i++){ct[idy][i] = 1.00 * ct[idy][i] / t;}ct[idy][idx] = 1.00 * ct[idy][idx] / t;// 最后更新单纯形表所有数据的值for(int i=0;i<n;i++){// 出基变量那一行已经更新过了,所以跳过if(i == idy) continue;double c=ct[i][idx];// 第一列的更新方法后后面的不同,所以单独写ct[i][0]-=c*ct[idy][0];for(int j=1;j<m;j++){// 入基变量那一列的值的更新方式也不同,单独写if(j==idx){ct[i][j]=ct[i][j]*(-ct[idy][idx]);continue;}// 其他的都一样ct[i][j]+=c*(-ct[idy][j]);}}cout<<"新一轮结果: "<<endl;for(int i=0;i<n;i++){for(int j=0;j<m;j++){cout<<ct[i][j]<<",";}cout<<endl;}cout<<"基本变量: ";for(int i=0;i<n-1;i++){cout<<"x"<<inx[i]<<",";}cout<<endl;cout<<"非基本变量: ";for(int i=0;i<m-1;i++){cout<<"x"<<ninx[i]<<",";}cout<<endl;
}int main(){cin>>n>>m;for(int i=0;i<n-1;i++){cin>>inx[i];}for(int i = 0;i<m-1;i++){cin>>ninx[i];}for(int i=0;i<n;i++){for(int j=0;j<m;j++){cin>>ct[i][j];}}while(true){// 如果非基本变量有正值则继续int flag=1;for(int i=1;i<m;i++){if(ct[0][i]>0) flag=0;}if(flag==1) break;// 执行单纯形算法solve();}// 为x赋值for(int i=0;i<m-1;i++){// 非基本变量全赋值为0x[ninx[i]-1] = 0;}for(int i=0;i<n-1;i++){// 基本变量赋值x[inx[i]-1] = ct[i+1][0];}cout<<"最优解为:x=(";for(int i=0;i<n+m-3;i++){cout<<x[i]<<",";}cout<<x[n+m-3]<<")"<<endl;cout<<"最优值为:z="<<-ct[0][0]<<endl;return 0;
}

本篇使用单纯形算法求解简单的线性规划问题就到此结束了,对于本文使用的例子所实现的代码其实还是欠妥的,这里是最大化目标,如果是最小化呢?这就需要更改一些地方了,具体有机会再探讨吧!

线性规划问题的单纯形算法求解相关推荐

  1. 线性规划专题——SIMPLEX 单纯形算法(三)图解——示例、注意点

    线性规划专题--SIMPLEX 单纯形算法(一) 线性规划专题--SIMPLEX 单纯形算法(二) 前面两篇博文已经把单纯形算法里面的核心思想给解释清楚了,主要是要认识到在线性规划里面的以下几点: 目 ...

  2. 线性规划之二 —— 单纯形算法(详解)

    鸣谢dalao的教导 单纯形算法是求解线性规划的经典方法 虽然ta的执行时间在最坏的情况下并不是多项式,然而在实际中这个算法通常是相当快速的 实际上也非常简单,主要就三个步骤: 找到一个初始的基本可行 ...

  3. 0050算法笔记——【线性规划】单纯形算法(未完全实现)

    题外话:王晓东的<算法设计与分析>看到现在,终于遇到自己琢磨不透的代码了.这里粘出来,求大神指点迷津,将代码补充完整~ 1.线性规划问题及其表示 线性规划问题可表示为如下形式: 变量满足约 ...

  4. 一般线性规划问题的2阶段单纯形算法

    5.一般线性规划问题的2阶段单纯形算法 引入人工变量后的线性规划问题与原问题并不等价,除非所有zi都是0 .     为了解决这个问题,在求解时必须分2个阶段进行.     第一阶段用一个辅助目标函数 ...

  5. Nelder-Mead(simplex,“单纯形”)算法

    求多维函数极值的一种算法,由Nelder和Mead提出,又叫单纯形算法,但和线性规划中的单纯形算法是不同的,由于未利用任何求导运算,算法比较简单,但收敛速度较慢,适合变元数不是很多的方程求极值,算法的 ...

  6. 线性规划-单纯形算法详解

    本文作者: hrwhisper 本文链接: https://www.hrwhisper.me/introduction-to-simplex-algorithm/ 版权声明: 本博客所有文章除特别声明 ...

  7. 简单理解线性规划的单纯形算法

    自己写的,csdn的markdown不怎么会用,所以在知乎写的. 文章-理解线性规划的单纯形算法

  8. 线性规划:单纯形算法之处理退化

    上一篇文章介绍了单纯形算法(<线性规划:单纯形算法>),但是还有一些遗留问题没有解决,比如退化情形(Degeneracy). 本文介绍如何处理退化情形. 退化情形 从几何上看上看,造成退化 ...

  9. 原始-对偶(Primal-Dual)算法求解线性规划

    ​原始-对偶(Primal-Dual)算法(Dantzig, Ford, and Fulkerso,1956)是用来求解线性规划的一种算法,可以看作是单纯形法的一种变体,目的是减少迭代次数. 构建该算 ...

最新文章

  1. 了解下SOAP Header 元素
  2. 一秒解决CentOS下service 功能 不能使用 bash: service: command not found
  3. 东京奥运会的官网的最上面是广告栏
  4. Web Api 如何做上传文件的单元测试
  5. tornado-简介和原理
  6. [BI项目记]-搭建代码管理环境之客户端
  7. 智慧农业IOT-onenet平台简单介绍
  8. discuzq 去除页面版权
  9. excel只显示公式,不显示结果
  10. 程序人生 - 为了避免惹上官司,你可以在这些免版权图片网站里寻找素材
  11. 国家利息中的等额本息和等额本金计算算法
  12. 图谱实战 | 再谈图谱表示:图网络表示GE与知识图谱表示KGE的原理对比与实操效果分析...
  13. IOS OpenGL ES GPUImage 图像Lanczos重取样模糊效果 GPUImageLanczosResamplingFilter
  14. 微信小程序全栈开发实践 第二章 微信小程序组件介绍及使用 -- 2.9 页面链接组件,如何自定义一个导航栏?
  15. 静态成员和静态成员函数的总结
  16. APP超级签名分发系统 企业签名免签封装微信多开自助分发多合一系统
  17. JAVA基础再回首(一)——基本概念、JAVA开发工具、JAVA基本语法
  18. 如何分析个股基本面_如何分析股票基本面
  19. 我室友打了一把王者我6分钟搞会了eclipse安装与配置
  20. 销售管理岗位竞聘PPT模板

热门文章

  1. RICO BOARD驱动探索之旅_环境搭建与点亮LED
  2. 无线传感器网络思维导图
  3. Python微信自动回复机器人
  4. ​stm32单片机真的可以取代51单片机吗?​
  5. IDEA中使用Junit测试并提高覆盖率
  6. 从MFQ方法到需求分析
  7. ( Flywest or AdvanceEdu )VS 看雪软件安全论坛
  8. 汉语的伟大, 给崇英语的人
  9. 用机器学习识别不断变化的股市状况—隐马尔可夫模型(HMM)股票指数预测实战
  10. 敏捷环境中的TMMi之5-测试策略