约 30 分钟 · 需要第1章的标准型与基本可行解

读完你能: 写出初始单纯形表;按“最负检验数进基、最小比值出基、主元消元”完成迭代;处理带 ≥\ge 和 == 约束的问题;从最终表读出最优解、最优值和影子价格;判断无可行解、无界、多重最优和退化。

主线例子: 工厂生产 A、B 两种产品,单件利润 40、30;机器工时 2x1+x2≤1002x_1+x_2\le100,人工工时 x1+2x2≤80x_1+2x_2\le80。

1. 单纯形法在做什么

第1章说过:最优解一定在某个基本可行解(顶点)上。单纯形法就是从一个基本可行解出发,每次换掉一个基变量,走到相邻且目标更好的顶点,直到没有更好的邻居为止。

拖动滑块,再点“下一步”,看单纯形法如何沿着顶点走到最优:

交互演示加载中…(需要启用 JavaScript)

每一次迭代只回答三个问题:

  1. 往哪走? 哪个非基变量增大能让目标改进最快——选它进基。
  2. 走多远? 进基变量增大时,哪个基变量最先降到 0——它出基。
  3. 怎么到? 用初等行变换把进基变量那一列变成单位列(主元消元)。

2. 单纯形表从哪来

把问题写成标准型(第1章):

min⁡ z=CTX,AX=B,X≥0.\min\ z=C^{T}X,\qquad AX=B,\qquad X\ge0 .

设当前基变量组成 X0X_0,它们的目标系数组成 C0C_0。初始时基变量是松弛变量或人工变量,对应的列恰好构成单位矩阵,于是单纯形表是

XTX^{T}
X0X_0 AA BB
检验行 CT−C0TAC^{T}-C_0^{T}A −C0TB-C_0^{T}B

最后一行每个元素叫检验数(reduced cost),表示“这个变量增加 1 单位,目标 zz 改变多少”。最后一行最后一列是 −z-z 的当前值。

对最小化问题:

  • 某个检验数为负,说明让该变量进基能让 zz 下降——还没到最优。
  • 所有检验数都 ≥0\ge0 时,任何变量进基都不会让 zz 更小——当前解最优。

最大化问题有两种等价处理:一是把目标乘 −1-1 变成最小化,解完再把最优值乘 −1-1;二是把检验行的符号全部取反(即 C0TA−CTC_0^{T}A-C^{T}),判别规则不变——仍然是“有负数就继续,全部非负就停”。

3. 单纯形法的五步

  1. 在检验行(不含最后一列)找最负的数,它所在的列叫工作列,对应变量进基。
  2. 用工作列中大于 0 的系数去除同一行的右端,最小比值所在行的元素是主元,该行的基变量出基。若工作列没有正系数,问题无界。
  3. 用初等行变换把主元化为 1,把工作列其他元素(包括检验行)都化为 0。
  4. 在基变量栏中用进基变量替换出基变量。
  5. 重复,直到检验行没有负数。此时基变量取右端的值,其余变量为 0。

为什么必须取最小比值

进基变量从 0 增大到 tt 时,第 ii 行的基变量变成 bi−aijtb_i-a_{ij}t。只有 aij>0a_{ij}>0 的行会减小,它降到 0 的时刻是 t=bi/aijt=b_i/a_{ij}。取最小比值,才能保证走过去时所有基变量都还非负;取大了,就会有某个变量变成负数,跑出可行域。

4. 手算主线例子

最大化 40x1+30x240x_1+30x_2 等价于最小化 z=−40x1−30x2z=-40x_1-30x_2。加松弛变量 s1,s2s_1,s_2,初始基 X0=(s1,s2)X_0=(s_1,s_2),C0=(0,0)C_0=(0,0),检验行就是 CT=(−40,−30,0,0)C^{T}=(-40,-30,0,0)。

表 0:在原点 (0,0)(0,0)。

基 x1x_1 x2x_2 s1s_1 s2s_2 右端 比值
s1s_1 2 1 1 0 100 100/2 = 50
s2s_2 1 2 0 1 80 80/1 = 80
检验行 −40 −30 0 0 0

最负检验数 −40,x1x_1 进基;最小比值 50,s1s_1 出基;主元 2。

表 1:走到 (50,0)(50,0)。 第一行除以 2,再用它消去 s2s_2 行和检验行的 x1x_1:

基 x1x_1 x2x_2 s1s_1 s2s_2 右端 比值
x1x_1 1 1/2 1/2 0 50 50 ÷ 1/2 = 100
s2s_2 0 3/2 −1/2 1 30 30 ÷ 3/2 = 20
检验行 0 −10 20 0 2000

右下角 2000 是 −z-z,即当前利润 2000。x2x_2 的检验数 −10 还为负,x2x_2 进基,s2s_2 出基,主元 3/2。

表 2:走到 (40,20)(40,20),最优。

基 x1x_1 x2x_2 s1s_1 s2s_2 右端
x1x_1 1 0 2/3 −1/3 40
x2x_2 0 1 −1/3 2/3 20
检验行 0 0 50/3 20/3 2200

检验行全部非负,停止。最优解 x1=40, x2=20x_1=40,\ x_2=20,最大利润 2200。 两条资源都用满(s1=s2=0s_1=s_2=0)。

最终表里的影子价格

检验行中松弛变量的系数 50/3、20/3 是两种资源的影子价格:机器工时每增加 1 小时,最大利润增加约 16.67;人工工时每增加 1 小时,增加约 6.67。这个结论在“最优基不变”的范围内成立,范围怎么算见第3章。

5. 大 M 法

当约束含 ≥\ge 或 == 时,需要人工变量当初始基(第1章第5节)。为了让人工变量最终为 0,在目标中给它们大惩罚:最小化加 +Ma+Ma,最大化加 −Ma-Ma。

例1: min⁡ z=2x1+3x2\min\ z=2x_1+3x_2,x1+x2≥4x_1+x_2\ge4,x1+3x2≥6x_1+3x_2\ge6,x1,x2≥0x_1,x_2\ge0。

标准型:x1+x2−e1+a1=4x_1+x_2-e_1+a_1=4,x1+3x2−e2+a2=6x_1+3x_2-e_2+a_2=6,目标 z=2x1+3x2+Ma1+Ma2z=2x_1+3x_2+Ma_1+Ma_2。初始基 (a1,a2)(a_1,a_2),C0=(M,M)C_0=(M,M)。

检验行 CT−C0TAC^{T}-C_0^{T}A 中每一项都形如“常数 + 系数·MM”。把它拆成两行会清楚得多:上面一行放不含 MM 的部分,下面一行放 MM 的系数。

表 0:

基 x1x_1 x2x_2 e1e_1 e2e_2 a1a_1 a2a_2 右端
a1a_1 1 1 −1 0 1 0 4
a2a_2 1 3 0 −1 0 1 6
常数行 2 3 0 0 0 0 0
M 行 −2 −4 1 1 0 0 −10

例如 x1x_1 列的检验数是 2−M⋅1−M⋅1=2−2M2-M\cdot1-M\cdot1=2-2M,拆成常数 2 和 MM 系数 −2。

选进基变量时先看 M 行:MM 远大于任何常数,所以 M 行最负的 −4 决定 x2x_2 进基。比值 4/1 = 4、6/3 = 2,a2a_2 出基。

表 1:

基 x1x_1 x2x_2 e1e_1 e2e_2 a1a_1 a2a_2 右端
a1a_1 2/3 0 −1 1/3 1 −1/3 2
x2x_2 1/3 1 0 −1/3 0 1/3 2
常数行 1 0 0 1 0 −1 −6
M 行 −2/3 0 1 −1/3 0 4/3 −2

M 行最负的是 −2/3,x1x_1 进基;比值 2÷23=32\div\frac23=3、2÷13=62\div\frac13=6,a1a_1 出基。

表 2:

基 x1x_1 x2x_2 e1e_1 e2e_2 a1a_1 a2a_2 右端
x1x_1 1 0 −3/2 1/2 3/2 −1/2 3
x2x_2 0 1 1/2 −1/2 −1/2 1/2 1
常数行 0 0 3/2 1/2 −3/2 −1/2 −9
M 行 0 0 0 0 1 1 0

M 行已没有负数,人工变量全部出基;再看常数行中 M 行为 0 的位置(x1,x2,e1,e2x_1,x_2,e_1,e_2),也都非负——最优。**x1=3, x2=1x_1=3,\ x_2=1,z=9z=9**(右下角 −9 是 −z-z)。a1,a2a_1,a_2 列的常数行虽然是负数,但它们的 M 行系数为 1,真实检验数是 M−32>0M-\frac32>0,不会进基。

6. 两阶段法

把“先看 M 行,再看常数行”的规则单独写出来,就是两阶段法:

  • 第一阶段: 只看 M 行(相当于最小化人工变量之和 a1+a2+⋯a_1+a_2+\cdots),用单纯形法把所有人工变量赶出基、取 0。人工变量一旦出基,就把它的整列删掉,不再让它回来。若第一阶段最优值为 0,但仍有取值为 0 的人工变量留在基中,应先用非人工列把它换出;该行若无可用主元,则它是可删除的冗余约束。
  • 第二阶段: M 行全为 0 后把它删掉,从此时的基本可行解出发,按常数行(原目标)继续单纯形法,直到常数行没有负数。

规则汇总:

情况 处理
M 行还有负数 按 M 行最负的列进基(第一阶段)
M 行没有负数 在 M 行为 0 的列中,按常数行最负的列进基(第二阶段)
人工变量出基 删除该列
M 行全为 0 删除 M 行
第一阶段结束时还有取正值的人工变量 原问题无可行解

最大化问题的人工变量系数怎么定? 在原目标里,最大化问题给人工变量 −M-M(越大越亏),最小化问题给 +M+M。如果先把最大化乘 −1-1 改成最小化,那么人工变量的系数也随之变成 +M+M,第一阶段的目标始终是“最小化人工变量之和”。两种写法指向同一件事:人工变量越大,目标越差。

例2:含等式约束。

min⁡ z=4x1+5x2,x1+x2=8,x1+2x2≥10,x1≤6,x1,x2≥0.\min\ z=4x_1+5x_2,\qquad x_1+x_2=8,\qquad x_1+2x_2\ge10,\qquad x_1\le6,\qquad x_1,x_2\ge0 .

标准型:x1+x2+a1=8x_1+x_2+a_1=8,x1+2x2−e1+a2=10x_1+2x_2-e_1+a_2=10,x1+s1=6x_1+s_1=6。初始基 (a1,a2,s1)(a_1,a_2,s_1)。

基 x1x_1 x2x_2 e1e_1 s1s_1 a1a_1 a2a_2 右端
a1a_1 1 1 0 0 1 0 8
a2a_2 1 2 −1 0 0 1 10
s1s_1 1 0 0 1 0 0 6
常数行 4 5 0 0 0 0 0
M 行 −2 −3 1 0 0 0 −18

M 行 −3 最负,x2x_2 进基;比值 8、5,a2a_2 出基,删去 a2a_2 列:

基 x1x_1 x2x_2 e1e_1 s1s_1 a1a_1 右端
a1a_1 1/2 0 1/2 0 1 3
x2x_2 1/2 1 −1/2 0 0 5
s1s_1 1 0 0 1 0 6
常数行 3/2 0 5/2 0 0 −25
M 行 −1/2 0 −1/2 0 0 −3

M 行 x1x_1 和 e1e_1 并列 −1/2,取 x1x_1。比值 3÷12=63\div\frac12=6、5÷12=105\div\frac12=10、6÷1=66\div1=6——a1a_1 与 s1s_1 并列最小,任选其一;选 a1a_1 出基,删去 a1a_1 列,M 行变为全 0,删去:

基 x1x_1 x2x_2 e1e_1 s1s_1 右端
x1x_1 1 0 1 0 6
x2x_2 0 1 −1 0 2
s1s_1 0 0 −1 1 0
常数行 0 0 1 0 −34

常数行全部非负,最优:**x1=6, x2=2x_1=6,\ x_2=2,z=34z=34。** 注意基变量 s1=0s_1=0——这就是比值并列带来的退化:顶点 (6,2)(6,2) 上同时有三条约束取等号(x1+x2=8x_1+x_2=8、x1+2x2=10x_1+2x_2=10、x1=6x_1=6)。

7. 从表上识别特殊情况

无可行解。 min⁡ z=x1+x2\min\ z=x_1+x_2,x1+x2≤2x_1+x_2\le2,2x1+3x2≥122x_1+3x_2\ge12。

基 x1x_1 x2x_2 s1s_1 e1e_1 a1a_1 右端
s1s_1 1 1 1 0 0 2
a1a_1 2 3 0 −1 1 12
M 行 −2 −3 0 1 0 −12

x2x_2 进基,比值 2 与 4,s1s_1 出基,得到

基 x1x_1 x2x_2 s1s_1 e1e_1 a1a_1 右端
x2x_2 1 1 1 0 0 2
a1a_1 −1 0 −3 −1 1 6
M 行 1 0 3 1 0 −6

M 行已无负数,第一阶段结束,但人工变量 a1=6a_1=6 仍在基中且为正——原问题无可行解。几何上,x1+x2≤2x_1+x_2\le2 的区域里 2x1+3x22x_1+3x_2 最大只有 6,达不到 12。

无界。 min⁡ z=−2x1−x2\min\ z=-2x_1-x_2,x1−x2≤2x_1-x_2\le2,−2x1+x2≤4-2x_1+x_2\le4。一次迭代后(x1x_1 进基、s1s_1 出基):

基 x1x_1 x2x_2 s1s_1 s2s_2 右端
x1x_1 1 −1 1 0 2
s2s_2 0 −1 2 1 8
检验行 0 −3 2 0 4

x2x_2 检验数 −3 要进基,但它这一列没有正系数,比值检验做不下去:x2x_2 可以无限增大而所有基变量都不会降到 0,zz 可以无限减小——问题无界。

多重最优。 最终表中,如果某个非基变量的检验数为 0,并且沿该方向能走正的步长,就能得到另一个不同的最优解。若只能做零步长的退化换基,还不能仅凭零检验数断定有不同的最优解。第1章例1把利润改成 40x+40y40x+40y 就会出现这种情况。

退化。 某个基变量取值为 0(如例2的 s1s_1)。退化时迭代可能“原地换基”而目标不变,极少数情况下会循环。实际手算中遇到比值并列,任选其一通常就能继续;要严格避免循环,可用 Bland 规则:在所有检验数为负的可入基变量中选下标最小的,再在最小比值并列时选下标最小的基变量出基;只对并列情况打破平局还不是完整规则。

8. 小结

  • 单纯形表 = [A ∣ B][A\ |\ B] + 检验行 CT−C0TAC^{T}-C_0^{T}A;右下角是 −z-z。
  • 最小化:检验数有负就继续,全部非负就停。最大化:乘 −1-1 变成最小化,或把检验行取反。
  • 一轮迭代:最负检验数进基 → 最小正比值出基 → 主元消元。
  • 人工变量要么用 ±M\pm M 惩罚(大 M 法),要么先单独最小化它们的和(两阶段法);把 M 行单独写出来,两者就是同一套计算。
  • 第一阶段结束人工变量仍为正 → 无可行解;进基列无正系数 → 无界;非基检验数为 0 → 多重最优;基变量为 0 → 退化。

自测

1. 主线例子的最终表中,如果人工工时从 80 增加到 86,最大利润是多少?最优基还成立吗?

用最终表中松弛变量的列:s2s_2 列是 (−1/3, 2/3)(-1/3,\ 2/3)。右端变化 Δ=6\Delta=6 时,新右端为 40−13⋅6=3840-\frac13\cdot6=38、20+23⋅6=2420+\frac23\cdot6=24,都非负,最优基不变。最大利润增加 203×6=40\frac{20}{3}\times6=40,变成 2240。直接验算:40⋅38+30⋅24=1520+720=224040\cdot38+30\cdot24=1520+720=2240。

2. 例1中为什么 a1、a2 列的常数行出现负数(−3/2、−1/2),却不需要让它们进基?

它们的真实检验数是“常数 + M 系数 × M”,即 −32+M-\frac32+M 与 −12+M-\frac12+M。MM 是足够大的正数,所以两者都为正。判断时先看 M 行:M 行为正的列不能进基,常数行只在 M 行为 0 的列上起作用。两阶段法中这两列早已删除,更不会出现这个疑问。

3. 用单纯形法求 max z = 3x1 + 2x2(约束 x1 + x2 ≤ 4,x1 + 3x2 ≤ 6),并与第1章例4的枚举结果对比。

改为最小化 −3x1−2x2-3x_1-2x_2。初始表检验行 (−3,−2,0,0)(-3,-2,0,0),x1x_1 进基,比值 4/1=44/1=4、6/1=66/1=6,s1s_1 出基。新表:x1x_1 行 (1,1,1,0 ∣ 4)(1,1,1,0\ |\ 4),s2s_2 行 (0,2,−1,1 ∣ 2)(0,2,-1,1\ |\ 2),检验行 (0,1,3,0 ∣ 12)(0,1,3,0\ |\ 12)。检验行全部非负,最优 x1=4, x2=0x_1=4,\ x_2=0,z=12z=12,只用了一次迭代就到达枚举表中的最优顶点 (4,0)(4,0)。