设等式约束优化问题
{ minimize f ( x ) s.t. h ( x ) = o ( 1 ) \begin{cases} \text{minimize}\quad f(\boldsymbol{x})\\ \text{s.t. }\quad\quad\boldsymbol{h}(\boldsymbol{x})=\boldsymbol{o} \end{cases}\quad\quad{(1)} {minimizef(x)s.t. h(x)=o(1)
其中 f : R n → R f:\text{R}^n\rightarrow\text{R} f:Rn→R, h : R n → R l \boldsymbol{h}:\text{R}^n\rightarrow\text{R}^l h:Rn→Rl,在 R n \text{R}^n Rn上连续。可行域 Ω = { x ∣ h ( x ) = o } \Omega=\{\boldsymbol{x}|\boldsymbol{h}(\boldsymbol{x})=\boldsymbol{o}\} Ω={x∣h(x)=o}。构造罚函数
P ( x ) = 1 2 h ( x ) ⊤ h ( x ) P(\boldsymbol{x})=\frac{1}{2}\boldsymbol{h}(\boldsymbol{x})^\top\boldsymbol{h}(\boldsymbol{x}) P(x)=21h(x)⊤h(x)
称 R n → R \text{R}^n\rightarrow\text{R} Rn→R函数
F ( x , σ ) = f ( x ) + σ P ( x ) F(\boldsymbol{x},\sigma)=f(\boldsymbol{x})+\sigma P(\boldsymbol{x}) F(x,σ)=f(x)+σP(x)
为问题(1)的增广目标函数,其中 σ > 0 \sigma>0 σ>0,称为罚因子。注意到 F ( x , σ ) = f ( x ) F(\boldsymbol{x},\sigma)=f(\boldsymbol{x}) F(x,σ)=f(x),当且仅当 x ∈ Ω \boldsymbol{x}\in\Omega x∈Ω。考虑无约束优化问题
{ minimize F ( x , σ ) s.t. x ∈ R n , ( 2 ) \begin{cases} \text{minimize}\quad F(\boldsymbol{x},\sigma)\\ \text{s.t.\ \ }\quad\quad\boldsymbol{x}\in\text{R}^n \end{cases},\quad\quad{(2)} {minimizeF(x,σ)s.t. x∈Rn,(2)
称为(1)的子问题。给定罚因子 σ > 0 \sigma>0 σ>0,设子问题(2)最优解 x σ = arg min x ∈ R n F ( x , σ ) \boldsymbol{x}_{\sigma}=\arg\min\limits_{\boldsymbol{x}\in\text{R}^n}F(\boldsymbol{x},\sigma) xσ=argx∈RnminF(x,σ)。若 x σ ∈ Ω \boldsymbol{x}_{\sigma}\in\Omega xσ∈Ω,则 σ P ( x σ ) = 0 \sigma P(\boldsymbol{x}_{\sigma})=0 σP(xσ)=0,且 F ( x σ , σ ) = f ( x σ ) F(\boldsymbol{x}_{\sigma},\sigma)=f(\boldsymbol{x}_{\sigma}) F(xσ,σ)=f(xσ)。故 x σ \boldsymbol{x}_{\sigma} xσ可以视为 f ( x ) f(\boldsymbol{x}) f(x)最优解的近似值。否则,即 x σ ∉ Ω \boldsymbol{x}_{\sigma}\not\in\Omega xσ∈Ω,则 σ P ( x σ ) \sigma P(\boldsymbol{x}_\sigma) σP(xσ)是一个正数,其存在是对 x σ \boldsymbol{x}_\sigma xσ脱离 Ω \Omega Ω的一种“惩罚”。此时,若加大 σ ′ > σ \sigma'>\sigma σ′>σ,再次尝试求解子问题 x σ ′ = arg min x ∈ R n F ( x , σ ′ ) \boldsymbol{x}_{\sigma'}=\arg\min\limits_{\boldsymbol{x}\in\text{R}^n} F(\boldsymbol{x},\sigma') xσ′=argx∈RnminF(x,σ′),意欲迫使 x σ ′ \boldsymbol{x}_{\sigma'} xσ′向 Ω \Omega Ω靠拢。可以证明以下命题
定理1:若约束优化问题(1)存在唯一最优解 x 0 \boldsymbol{x}_0 x0,子问题(2)对任意 σ > 0 \sigma>0 σ>0,均有最优解 x σ \boldsymbol{x}_\sigma xσ。给定序列 0 < σ 1 < σ 2 < ⋯ < σ k < ⋯ 0<\sigma_1<\sigma_2<\cdots<\sigma_k<\cdots 0<σ1<σ2<⋯<σk<⋯,且 lim k → ∞ σ k = + ∞ \lim\limits_{k\rightarrow\infty}\sigma_k=+\infty k→∞limσk=+∞。按迭代式
x k = arg min x ∈ R n F ( x , σ k ) \boldsymbol{x}_k=\arg\min_{\boldsymbol{x}\in\text{R}^n}F(\boldsymbol{x},\sigma_k) xk=argx∈RnminF(x,σk)
算得序列 { x k } \{\boldsymbol{x}_k\} {xk},则必有
{ lim k → ∞ x k = x 0 lim k → ∞ σ k P ( x k ) = 0 . \begin{cases} \lim\limits_{k\rightarrow\infty}\boldsymbol{x}_k=\boldsymbol{x}_0\\ \lim\limits_{k\rightarrow\infty}\sigma_k P(\boldsymbol{x}_k)=0 \end{cases}. ⎩ ⎨ ⎧k→∞limxk=x0k→∞limσkP(xk)=0.
对一般的有约束优化问题
{ minimize f ( x ) s.t. h ( x ) = o g ( x ) ≥ o ( 3 ) \begin{cases} \text{minimize}\quad f(\boldsymbol{x})\\ \text{s.t.\ \ }\quad\quad\boldsymbol{h}(\boldsymbol{x})=\boldsymbol{o}\\ \quad\quad\quad\quad\boldsymbol{g}(\boldsymbol{x})\geq\boldsymbol{o} \end{cases}\quad\quad{(3)} ⎩ ⎨ ⎧minimizef(x)s.t. h(x)=og(x)≥o(3)
其中, f : R n → R f:\text{R}^n\rightarrow\text{R} f:Rn→R, h : R n → R l \boldsymbol{h}:\text{R}^n\rightarrow\text{R}^l h:Rn→Rl, g : R n → R m \boldsymbol{g}:\text{R}^n\rightarrow\text{R}^m g:Rn→Rm。 f ( x ) f(\boldsymbol{x}) f(x), h ( x ) \boldsymbol{h}(\boldsymbol{x}) h(x), g ( x ) \boldsymbol{g}(\boldsymbol{x}) g(x)在 R n \text{R}^n Rn上连续。可行域 Ω = { x ∣ h ( x ) = o , g ( x ) ≥ o } \Omega=\{\boldsymbol{x}|\boldsymbol{h}(\boldsymbol{x})=\boldsymbol{o},\boldsymbol{g}(\boldsymbol{x})\geq\boldsymbol{o}\} Ω={x∣h(x)=o,g(x)≥o}。定义罚函数
P ( x ) = h ( x ) ⊤ h ( x ) + g 1 ( x ) ⊤ g 1 ( x ) . P(\boldsymbol{x})=\boldsymbol{h}(\boldsymbol{x})^\top\boldsymbol{h}(\boldsymbol{x})+\boldsymbol{g}_1(\boldsymbol{x})^\top\boldsymbol{g}_1(\boldsymbol{x}). P(x)=h(x)⊤h(x)+g1(x)⊤g1(x).
其中, g 1 ( x ) = min ( o , g ( x ) ) = ( min ( 0 , g 1 ( x ) ) ⋮ min ( 0 , g m ( x ) ) ) \boldsymbol{g}_1(\boldsymbol{x})=\boldsymbol{\min}(\boldsymbol{o},\boldsymbol{g}(\boldsymbol{x}))=\begin{pmatrix}\min(0,g_1(\boldsymbol{x}))\\\vdots\\\min(0,g_m(\boldsymbol{x}))\end{pmatrix} g1(x)=min(o,g(x))= min(0,g1(x))⋮min(0,gm(x)) 。不难证实
{ P ( x ) = 0 x ∈ Ω P ( x ) > 0 x ∉ Ω , \begin{cases} P(\boldsymbol{x})=0&\boldsymbol{x}\in\Omega\\ P(\boldsymbol{x})>0&\boldsymbol{x}\not\in\Omega \end{cases}, {P(x)=0P(x)>0x∈Ωx∈Ω,
且在 R n \text{R}^n Rn上连续。取罚因子 σ > 0 \sigma>0 σ>0,定义增广目标函数:
F ( x , σ ) = f ( x ) + σ P ( x ) . F(\boldsymbol{x},\sigma)=f(\boldsymbol{x})+\sigma P(\boldsymbol{x}). F(x,σ)=f(x)+σP(x).
及子问题
{ minimize F ( x , σ ) s.t. x ∈ R n ( 4 ) \begin{cases} \text{minimize}\quad F(\boldsymbol{x},\sigma)\\ \text{s.t.}\quad\quad\quad\boldsymbol{x}\in\text{R}^n \end{cases}\quad\quad{(4)} {minimizeF(x,σ)s.t.x∈Rn(4)
则关于等式约束优化问题(1)及其子问题(2)的定理1的结论对问题(3)及其子问题(4)均成立。根据定理1,对问题(4)给定罚因子初始值 σ 1 > 0 \sigma_1>0 σ1>0(典型值为10)、放大系数 c > 1 c>1 c>1(典型值为2.5)及容错误差 ε > 0 \varepsilon>0 ε>0,按
x k + 1 = arg min x ∈ R n F ( x , σ k ) \boldsymbol{x}_{k+1}=\arg\min_{\boldsymbol{x}\in\text{R}^n}F(\boldsymbol{x},\sigma_k) xk+1=argx∈RnminF(x,σk)
做迭代,直至 σ k P ( x k ) < ε \sigma_k P(\boldsymbol{x}_k)<\varepsilon σkP(xk)<ε为止。所得当前 x k \boldsymbol{x}_k xk即为问题(3)的最优解近似值。由于罚函数是关于约束函数的二次式,故此算法常称为二次罚函数算法。该算法以一系列子问题的最优解来逼近问题的最优解,也被称为序列无约束极小化方法简记为SUMT方法。
下列代码实现罚函数算法。
import numpy as np #导入numpy
from scipy.optimize import minimize,OptimizeResult #导入minimize,OptimizeResult
def sumt(f, x1, h = None, g = None, eps = 1e-5):if not callable(h): #没有等式约束h = lambda x: np.zeros(1) #置零if callable(g):m = g(x1).size #g的维数zero = np.zeros(m)g1 = lambda x: np.minimum(zero, g(x)) #转换不等式约束else: #没有不等式约束g1 = lambda x: np.zeros(1) #置零sigmak = 10.0 #初始罚因子c = 2.5 #罚因子放大系数sPk = 10.0 #初始罚项k = 0 #初始迭代数xk = x1 #初始迭代解向量P = lambda x: 0.5 * (np.dot(h(x), h(x)) + np.dot(g1(x), g1(x))) #罚函数F = lambda x: f(x) + sigmak * P(x) #子问题目标函数while sPk >= eps: #迭代k += 1 #迭代次数自增1result = minimize(F,xk) #求解子问题xk = result.x #子问题最优解sPk = result.fun - f(xk) #罚项sigmak *= c #放大罚因子return OptimizeResult(fun = f(xk), x = xk, nit = k)
程序的第3~25行定义的sumt函数实现求解一般约束优化问题的二次罚函数算法(序列无约束极小化SUMT方法)。该函数的参数f,x1表示约束优化问题的目标函数 f ( x ) f(\boldsymbol{x}) f(x)和初始解向量 x 1 \boldsymbol{x}_1 x1。h表示等式约束函数 h ( x ) \boldsymbol{h}(\boldsymbol{x}) h(x)缺省值为None,表示优化问题无等式约束。g表示不等式约束函数 g ( x ) \boldsymbol{g}(\boldsymbol{x}) g(x),缺省值为None,表示问题无不等式约束。参数eps表示容错误差 ε \varepsilon ε。
函数体内第4~5行对无等式约束的情况将h置为零函数,以便统一代码。第6~11行的if-else语句根据是否有不等式约束,设置表示 g 1 ( x ) = min ( g ( x ) , o ) \boldsymbol{g}_1(\boldsymbol{x})=\boldsymbol{\min}(\boldsymbol{g}(\boldsymbol{x}),\boldsymbol{o}) g1(x)=min(g(x),o)便于统一代码的形式。第12~16行分别对罚因子 σ k \sigma_k σk、罚因子放大系数 c c c、罚项 σ k P ( x k ) \sigma_kP(\boldsymbol{x}_k) σkP(xk)、迭代次数 k k k及解向量 x k \boldsymbol{x}_k xk作初始化操作。第19~24行的while语句完成算法的迭代。其中,第21行调用scipy.optimize模块中的minimize函数求解子问题,返回值赋予result。第22行读取迭代解向量xk,第23行计算罚项 σ k P ( x k ) = F ( x k , σ k ) − f ( x k ) \sigma_kP(\boldsymbol{x}_k)=F(\boldsymbol{x}_k,\sigma_k)-f(\boldsymbol{x}_k) σkP(xk)=F(xk,σk)−f(xk),赋予sPk。第24行放大罚因子 σ k = c × σ k \sigma_k=c\times\sigma_k σk=c×σk。迭代结束,第25行返回问题的最优解近似值 x k \boldsymbol{x}_k xk、最优值近似值 f ( x k ) f(\boldsymbol{x}_k) f(xk)和迭代次数 k k k。
例1:用函数sumt求解求解线性规划
{ minimize x 1 − x 2 s.t. − x 1 + 2 x 2 + x 3 ≤ 2 − 4 x 1 + 4 x 2 − x 3 = 4 x 1 − x 3 = 0 x 1 , x 2 , x 3 ≥ 0 , \begin{cases} \text{minimize}\quad\quad x_1-x_2\\ \text{s.t.\ \ \ \ \ }\quad\quad -x_1+2x_2+x_3\leq2\\ \quad\quad\quad\quad\quad -4x_1+4x_2-x_3=4\\ \quad\quad\quad\quad\quad x_1-x_3=0\\ \quad\quad\quad\quad\quad x_1,x_2,x_3\geq0 \end{cases}, ⎩ ⎨ ⎧minimizex1−x2s.t. −x1+2x2+x3≤2−4x1+4x2−x3=4x1−x3=0x1,x2,x3≥0,
给定初始迭代点 x 1 = o \boldsymbol{x}_1=\boldsymbol{o} x1=o。
解:这个线性规划的数据矩阵为
c = ( 1 − 1 0 ) , A e q = ( − 4 4 − 1 1 0 − 1 ) , b e q = ( 4 0 ) , A i q = ( 1 − 2 − 1 1 0 0 0 1 0 0 0 1 ) , b i q = ( − 2 0 0 0 ) . \boldsymbol{c}=\begin{pmatrix}1\\-1\\0\end{pmatrix},\boldsymbol{A}_{eq}=\begin{pmatrix}-4&4&-1\\1&0&-1\end{pmatrix},\boldsymbol{b}_{eq}=\begin{pmatrix}4\\0\end{pmatrix},\boldsymbol{A}_{iq}=\begin{pmatrix}1&-2&-1\\1&0&0\\0&1&0\\0&0&1\end{pmatrix},\boldsymbol{b}_{iq}=\begin{pmatrix}-2\\0\\0\\0\end{pmatrix}. c= 1−10 ,Aeq=(−4140−1−1),beq=(40),Aiq= 1100−2010−1001 ,biq= −2000 .
于是
f ( x ) = c ⊤ x , h ( x ) = A e q − b e q , g ( x ) = A i q − b i p . f(\boldsymbol{x})=\boldsymbol{c}^\top\boldsymbol{x},\quad\boldsymbol{h}(\boldsymbol{x})=\boldsymbol{A}_{eq}-\boldsymbol{b}_{eq},\quad\boldsymbol{g}(\boldsymbol{x})=\boldsymbol{A}_{iq}-\boldsymbol{b}_{ip}. f(x)=c⊤x,h(x)=Aeq−beq,g(x)=Aiq−bip.
利用这些数据,下列代码完成计算。
import numpy as np #导入numpy
c = np.array([1, -1, 0]) #向量c
Ae = np.array([[-4, 4, -1], #矩阵Aeq[1, 0, -1]])
be = np.array([4, 0]) #向量beq
Ai = np.array([[1, -2, -1], #矩阵Aiq[1, 0, 0],[0, 1, 0],[0, 0, 1]])
bi = np.array([-2, 0, 0, 0]) #向量biq
f = lambda x: np.dot(c, x) #目标函数
h = lambda x: np.matmul(Ae, x) - be #等式约束函数
g = lambda x: np.matmul(Ai, x) - bi #不等式约束函数
x1 = np.zeros(3) #初始迭代点
print(sumt(f, x1, h, g))
借助代码内的注释信息,不难理解本程序。第15行调用sumt函数,计算问题最优解近似值并输出。运行程序,输出
fun: -1.0000094540269446nit: 8x: array([-6.39954354e-06, 1.00000305e+00, 6.29523189e-06])
意味着经过8次迭代,算得本问题的最优解为 x 0 = ( 0 1 0 ) \boldsymbol{x}_0=\begin{pmatrix}0\\1\\0\end{pmatrix} x0= 010 ,最优解处函数值为 f ( x 0 ) = − 1 f(\boldsymbol{x}_0)=-1 f(x0)=−1。
例2:用sumt函数求解二次规划
{ minimize x 1 2 + x 1 x 2 + 2 x 2 2 + x 3 2 − 6 x 1 − 2 x 2 − 12 x 3 s.t. x 1 + x 2 + x 3 − 2 = 0 x 1 − 2 x 2 + 3 ≥ 0 x 1 , x 2 , x 3 ≥ 0 , \begin{cases} \text{minimize}\quad x_1^2+x_1x_2+2x_2^2+x_3^2-6x_1-2x_2-12x_3\\ \text{s.t.\ \ }\quad\quad\quad x_1+x_2+x_3-2=0\\ \quad\quad\quad\quad\quad x_1-2x_2+3\geq0\\ \quad\quad\quad\quad\quad x_1,x_2,x_3\geq0 \end{cases}, ⎩ ⎨ ⎧minimizex12+x1x2+2x22+x32−6x1−2x2−12x3s.t. x1+x2+x3−2=0x1−2x2+3≥0x1,x2,x3≥0,
给定初始可行解 x 1 = ( 1 1 0 ) \boldsymbol{x}_1=\begin{pmatrix}1\\1\\0\end{pmatrix} x1= 110 。
解:本二次规划的数据矩阵为
H = ( 2 1 0 1 4 0 0 0 2 ) , c = ( − 6 − 2 − 12 ) A e q = ( 1 1 1 ) , b e q = ( 2 ) A i q = ( 1 − 2 0 1 0 0 0 1 0 0 0 1 ) , b i q = ( − 3 0 0 0 ) \begin{array}{l} \boldsymbol{H}=\begin{pmatrix}2&1&0\\1&4&0\\0&0&2\end{pmatrix},\boldsymbol{c}=\begin{pmatrix}-6\\-2\\-12\end{pmatrix}\\ \boldsymbol{A}_{eq}=\begin{pmatrix}1&1&1\end{pmatrix},\boldsymbol{b}_{eq}=(2)\\ \boldsymbol{A}_{iq}=\begin{pmatrix}1&-2&0\\1&0&0\\0&1&0\\0&0&1\end{pmatrix},\boldsymbol{b}_{iq}=\begin{pmatrix}-3\\0\\0\\0\end{pmatrix} \end{array} H= 210140002 ,c= −6−2−12 Aeq=(111),beq=(2)Aiq= 1100−20100001 ,biq= −3000
下列代码完成计算。
import numpy as np #导入numpy
H = np.array([[2, 1, 0], #矩阵H[1, 4, 0],[0, 0, 2]])
c = np.array([-6, -2, -12]) #向量c
Ae = np.array([[1, 1, 1]]) #矩阵Aeq
be = np.array([2]) #向量beq
Ai = np.array([[-1, -2, 0], #矩阵Aiq[1, 0, 0],[0, 1, 0],[0, 0, 1]])
bi = np.array([-3, 0, 0, 0]) #向量biq
x1 = np.array([1, 1, 0]) #初始迭代点
f = lambda x: 0.5 * np.matmul(x, np.matmul(H, x)) + np.matmul(c, x) #目标函数
h = lambda x: np.matmul(Ae, x) - be #等式约束函数
g = lambda x: np.matmul(Ai, x) - bi #不等式约束函数
print(sumt(f, x1, h, g))
对照代码内的注释信息,不难理解程序。运行程序,输出
fun: -20.000011166902542nit: 16x: array([-2.22198421e-07, -6.51694981e-07, 2.00000173e+00])
这意味着经过16次迭代,算得本问题的最优解 x 0 = ( 0 0 2 ) \boldsymbol{x}_0=\begin{pmatrix}0\\0\\2\end{pmatrix} x0= 002 ,最优值 f ( x 0 ) = − 20 f(\boldsymbol{x}_0)=-20 f(x0)=−20。
例3:用sumt函数求解优化问题
{ minimize x 1 2 + x 2 2 − 16 x 1 − 10 x 2 s.t. − x 1 2 + 6 x 1 − 4 x 2 + 11 ≥ 0 x 1 x 2 − 3 x 2 − e x 1 − 3 + 1 ≥ 0 x 1 , x 2 ≥ 0 , \begin{cases} \text{minimize}\quad x_1^2+x_2^2-16x_1-10x_2\\ \text{s.t.\ \ }\quad\quad\quad -x_1^2+6x_1-4x_2+11\geq0\\ \quad\quad\quad\quad\quad x_1x_2-3x_2-e^{x_1-3}+1\geq0\\ \quad\quad\quad\quad\quad x_1,x_2\geq0 \end{cases}, ⎩ ⎨ ⎧minimizex12+x22−16x1−10x2s.t. −x12+6x1−4x2+11≥0x1x2−3x2−ex1−3+1≥0x1,x2≥0,
给定初始迭代点 x 1 = o \boldsymbol{x}_1=\boldsymbol{o} x1=o。
解:下列代码完成计算:
import numpy as np #导入numpy
f = lambda x: x[0] ** 2 + x[1] ** 2 - 16 * x[0] - 10 * x[1] #目标函数
g = lambda x: np.array([-x[0] ** 2 + 6 * x[0] - 4 * x[1] + 11, #不等式约束函数x[0] * x[1] - 3 * x[1] - np.exp(x[0] - 3) + 1,x[0],x[1]])
x1 = np.zeros(2) #初始迭代点
print(sumt(f, x1, g = g))
借助代码内注释信息,不难理解本程序。需要注意,本问题只有不等式约束g,第8行调用sumt时应表示等式约束的参数h使用缺省值,在其后的不等式约束参数g须使用赋值形式传递。运行程序,输出
fun: -79.80782889081777nit: 11x: array([5.23961012, 3.74603874])
意味着经过11次迭代,算得线性规划问题最优解近似值 x 0 = ( 5.3296 3.7460 ) \boldsymbol{x}_0=\begin{pmatrix}5.3296\\3.7460\end{pmatrix} x0=(5.32963.7460),最优值 f ( x 0 ) ≈ − 79.8078 f(\boldsymbol{x}_0)\approx-79.8078 f(x0)≈−79.8078。
写博不易,敬请支持:
如果阅读本文于您有所获,敬请点赞、评论、收藏,谢谢大家的支持!