为了更加容易地理解单纯形法,下面我结合一个例子,来讲解单纯形法的思路和实现过程。
对于有界线性规划问题,我们可以想办法计算每个约束线交汇的交点,然后取这些交点中最大的目标函数值,就得到线性规划问题的最优解。
首先我们引入松弛变量。引入松弛变量使所有约束方程从不等式变成等式。
举例来说,对于约束约束
可以定义一个松弛变量S1,将其加到约束条件的左边,得到如下关系:
分析一下松弛变量:如果它是正数,表示我们在这个约束条件下还有些放松的余地,还有一些资源没有完全使用。如果它是负数,表示我们己经超过了这个约束条件。如果它是零,表示我们刚好达到这个约束条件。
以这样一组不等式为例来说明:
目标函数为:
其可行解域如下图所示:
两个约束线的交点,称为极点。有些极点在可行解域外(如F),予以忽略;有些在可行解域边界上,这样的就是可行极点(如ABDCE)。只要我们计算出所有可行极点处的目标函数值,取其中最大的,就能得到线性规划问题的最优解。
如何得到各个极点的坐标?
对每个约束方程引入一个不同的松弛变量,最终约束优化问题变为下面的形式:
在上述方程组中,加上松弛变量,共有6个变量,但是只有4个方程。该方程组是欠定的。
未知数个数和方程个数之差(本例中为2)直接关系到如何识别可行极点。
由于本例中未知数个数和方程个数之差为2,因此必须固定其中2个变量,令其为0,然后通过解方程组计算其余变量的值。这样就能得到其中一个极点。
例如,上述方程组中,我们令x1和s4为0,于是得到方程组:
可以解出:得到x2=6,S1=11,S2=32和S3=9。对应了极点E点。
同样,令x1和x2为0,对应A点;x1和S2为0,对应B点;S1和S2为0,对应C点;S1和S4为0,对应D点。
6个参数,两两参数为0,组合起来共有15种情况,对应15个点。但其中只有ABCDE的5个点是可行极点,其余的都是无效的极点。
如果计算所有的极点,必然导致效率较低。那么,能否只计算那些可行的极点?
答案是,当然可以。
如何计算那些可行的极点?
总结一下上面的过程,先设置n-m个变量为0,然后求解剩下的m个变量m个等式的方程组。这里,我们将取零值的变量一般称为非基本变量,其他m个变量称为基本变量。如果所有的基本变量是非负的,那么这个结果称为基本可行解。最优解就是这些基本可行解中的一个。
单纯形法 就是,先找到求出一个基本可行解,然后逐渐增加目标函数值,求出其他基本可行解,最终达到最优解,同时算法终止。
第一步,先找到一个基本可行解,令x1=x2=0,得到方程组:
{ 7 x 1 + 11 x 2 + S 1 = 77 10 x 1 + 8 x 2 + S 2 = 80 x 1 + S 3 = 9 x 2 + S 4 = 6 \left \{ \begin{array}{r c l} 7x_1+11x_2+S_1=77\\ 10x_1+8x_2+ S_2=80 \\ x_1+S_3=9 \\ x_2+S_4=6 \\ \end{array} \right . ⎩⎪⎪⎨⎪⎪⎧7x1+11x2+S1=7710x1+8x2+S2=80x1+S3=9x2+S4=6
用高斯-约当法解方程组,得到解为: S 1 S_1 S1=77, S 2 S_2 S2=80, S 3 S_3 S3=9和 S 4 S_4 S4=6。
目标函数可以表示为:
Z − 150 x 1 − 175 x 2 − 0 S 1 − 0 S 2 − 0 S 3 − 0 S 4 = 0 Z-150x_1-175x_2-0S_1-0S_2-0S_3-0S_4=0 Z−150x1−175x2−0S1−0S2−0S3−0S4=0
目标函数值为: Z = 0 Z=0 Z=0。
第二步,移动到一个能使目标函数值增大的新可行解。很明显,增加当前非基本变量〔在这里是x1和x2)的值,Z值就会增大。
这里定义:把一个非基本变量变成基本(非零)变量,这个变量称为“进基变量〔entering rrariable)”。在处理过程中,如果一个基本变量变成非基本(零值)变量,该变量则称为“退基变poleaxing variable) "。
一般把最大负数值系数的变量选择为进基变量,因为这常常能使Z值的增加量最大。在本例中,由于x1的系数-175比x2的系数-150更小,所以x2成为进基变量。
这里,选择x2成为进基变量。选择哪个为退基变量呢?
我们需要计算上一步中,等号右边的值与 x 2 x2 x2的系数的比值,其实就是当前方程组在 x 2 x2 x2轴上的截距:
{ 7 x 1 + 11 x 2 + S 1 = 77 10 x 1 + 8 x 2 + S 2 = 80 x 1 + S 3 = 9 x 2 + S 4 = 6 \left \{ \begin{array}{r c l} 7x_1+11x_2+S1=77\\ 10x_1+8x_2+ S2=80 \\ x_1+S3=9 \\ x_2+S4=6 \\ \end{array} \right . ⎩⎪⎪⎨⎪⎪⎧7x1+11x2+S1=7710x1+8x2+S2=80x1+S3=9x2+S4=6
上述方程组的截距分别为:77/11=7;80/8=10;9/0= ∞ \infty ∞;6/1=6;
其中,最小截距为S4为基本变量的这个方程,因此将S4作为退基变量。其实就是相当于在可行解域图中找到了 x 2 x_2 x2轴上的截距最小的那个点,就是E点。
第三步,x2成为进基变量,S4作为退基变量后,用S4的方程作为主元行,消去方程组其他方程中的 x 2 x_2 x2的系数,得到新的方程组:
{ 7 x 1 + 11 x 2 + S 1 = 77 ( 不 含 x 2 , 未 变 ) 10 x 1 + S 2 − 8 S 4 = 32 ( 含 x 2 , 消 去 x 2 ) x 1 + S 3 = 9 ( 不 含 x 2 , 未 变 ) x 2 + S 4 = 6 ( 退 基 , 主 元 行 ) \left \{ \begin{array}{r c l} 7x_1+11x_2+S1=77(不含x_2,未变)\\ 10x_1+S2-8S4=32(含x_2,消去x_2) \\ x_1+S3=9(不含x_2,未变) \\ x_2+S4=6(退基,主元行) \\ \end{array} \right . ⎩⎪⎪⎨⎪⎪⎧7x1+11x2+S1=77(不含x2,未变)10x1+S2−8S4=32(含x2,消去x2)x1+S3=9(不含x2,未变)x2+S4=6(退基,主元行)
同时也消去目标函数中的 x 2 x_2 x2的系数,得到目标函数为:
Z − 150 x 1 − 0 x 2 − 0 S 1 − 0 S 2 − 0 S 3 + 175 S 4 = 1050 Z-150x_1-0x_2-0S_1-0S_2-0S_3+175S_4=1050 Z−150x1−0x2−0S1−0S2−0S3+175S4=1050
目标函数值为: Z = 1050 Z=1050 Z=1050。
第四步,重复上面第二步和第三步的方法,直到目标函数行不存在为负数的系数,结束。此时就是最优解。
目标函数方程 Z − 150 x 1 − 0 x 2 − 0 S 1 − 0 S 2 − 0 S 3 + 175 S 4 = 1050 Z-150x_1-0x_2-0S_1-0S_2-0S_3+175S_4=1050 Z−150x1−0x2−0S1−0S2−0S3+175S4=1050中,系数为负值的只有x1了,因此选取x1作为进基变量。
计算截距,77/11=7,32/10=3.2,9/1=0,6/0= ∞ \infty ∞;因此选第二个方程,S4已经是退基后的变量了,因此选S2作为退基变量。(此时,对应于可行解域图中D点。)
于是,用第二个方程作为主元行,消去 x 1 x_1 x1的系数,得到新的方程组,以及新的目标函数。
然后,再重复一次进基和退基之后,就能找到可行解域图中C点。然后消去得到新的方程组,以及新的目标函数后,目标函数中所有的系数都没有负数了,结束。此时,就得到最优解,就是在C点的位置。