线性规划之单纯形算法

学了很长时间,一直不是很能理解,所以就准备写一篇。
这篇文章只讲单纯形算法

假设我们已经得到了标准型:

max:i=1naixii=1nbj,ixi=cj,j=1,2mxi0,i=1,2n

而得到最优解的过程就是:
找到一个基变量和非基变量,将他们交换。我们通过不断地交换,不断地让答案更优。

这就是在凸壳上不断向最优解移动的过程。

先据一组数据作为具体的例子:

max:5x1+2x2

{30x1+20x2+x3=1605x1+x2+x4=15x1+x5=4x1,x2,x3,x4,x50

m 条限制,我们分别令 x3,x4,x5 为其基变量,x1,x2 为非基变量。
我们可以得到

max:5x1+2x2x3=16030x120x2x4=155x1x2x5=4x1

我们令所有的非基变量为 0,我们可以得到一组解 {x1=0x2=0x3=160x4=15x5=4

我们获得了一个小的可怜的答案——0
而在我们要最大化的答案中,x1x2 的系数均 >0,也就意味着,我们增大其中任何一个数又可以让答案变优,所以我们贪心地选择系数较大的 x1
我们把它从 0 增大到某一个正实数,我们需要找到它的上界,也就是在 x1 不断地增加的过程中,哪一个非基变量会先变成 0

仍然令其它非基变量是 0,我们可以得到三个基变量的限制:{x3=16030x1x4=155x1x5=4x1,他们分别要求 {x1163x13x14,其中最紧的限制为 x4,我们就将 x4 变成非基变量,把 x1 变成基变量。我们就需要用 x4 和其他的非基变量来替换 x1,根据等式 x4=155x1x2 可以得到 x1=315x415x2

替换可以得到新的限制:

max:15x4+x2x3=70+6x414x2x1=315x415x2x5=1+15x4+15x2

这个限制我们可以得到解 {x1=3x2=0x3=70x4=0x5=1
接下来我们继续重复这个过程,发现 x4 的系数是负的,我们交换它不会使得答案变优,所以我们只能替换 x2

仍然是有三条限制:{x3=7014x2x1=315x2x5=1+15x2,三个方程分别解出来为 {x25x215x25,显然第三条限制是没有用的,其中最紧的限制是 x3 的限制,所以考虑将 x2x3 进行交换,得到 x2=5114x3+37x4

替换得到:

max:2047x4114x3x2=5114x3+37x4x1=2170x327x4x5=6+170x3+27x4

发现剩下的两个系数都是 <0 了,所以这就是可能的最优解了。

我们抽象一下刚才的过程,我们就可以得到一个具体的过程了:
找到最大的系数 ai,如果其大于 0,我们找到所有对其限制最大的编号最小的一个基变量,将这两个变量进行一次交换,然后重复这个过程。

实现代码如下:

namespace XG{
    double a[50][50],tr;
    int n,m,ind[50];
    void turn(int x,int y)
    {
        for(int i=0;i<=n;i++)
            if(i!=x)
            {
                tr=a[i][y]/a[x][y];
                for(int j=1;j<=m;j++)
                    a[i][j]-=a[x][j]*tr;
            }
        tr=a[x][ind[x]=y];
        for(int i=1;i<=m;i++)
            a[x][i]/=tr;
    }
    double solve()
    {
        while(1)
        {
            double maxn=0,lim=1e18;
            int x=0,y=0;
            for(int i=1;i<=m;i++)
                if(a[0][i]>maxn)
                    x=i,maxn=a[0][i];
            if(!x) break;
            for(int i=1;i<=n;i++)
                if(a[i][x]>0&&lim>a[i][m]/a[i][x])
                    lim=a[i][m]/a[i][x],y=i;
            if(!y) break;
            turn(y,x);
        }
        return -a[0][m];
    }
}
posted @   Xun_Xiaoyao  阅读(55)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· winform 绘制太阳,地球,月球 运作规律
· 超详细:普通电脑也行Windows部署deepseek R1训练数据并当服务器共享给他人
· 上周热点回顾(3.3-3.9)
· AI 智能体引爆开源社区「GitHub 热点速览」
· 写一个简单的SQL生成工具
/* 鼠标点击求赞文字特效 */
点击右上角即可分享
微信分享提示