1、.动态规划方法的 matlab 实现及其应用(龙京鹏,张华庆,罗明良,刘水林) (南昌航空大学,数学与信息科学学院,江西,南昌)摘要:本文运用 matlab 语言实现了动态规划的逆序算法,根据状态变量的维数,编写了指标函数最小值的逆序算法递归计算程序。两个实例的应用检验了该程序的有效性,同时也表明了该算法程序对众多类典型的动态规划应用问题尤其是确定离散型的应用问题的通用性,提供了求解各种动态规划问题的有效工具。关键词:动态规划 基本方程的逆序算法 MATLAB 实现MATLAB Achieve For Dynamic Programming and Its Application(Jingpe
2、ngLong,HuaqingZhang,MingliangLuo,ShuilinLiu)(School of Mathematics and Information Science,Nanchang HangkongUniversity,Nanchang,China)Abstract:This article achieves the reverse algorithm of dynamic programming by using the matlab language,and prepares the recursive calculation program of reverse alg
3、orithm which thetargetfunctionvalueisthesmallest.Theapplicationoftwoexamplesshowthattheprogram is effective,and this algorithm program is general to many typical application of dynamic programming,especially the application of deterministic discrete.This algorithm program provides a effective tool t
4、o the solution of a variety of dynamic programming problems. Key words:dynamic programming;reverse algorithm;Matlab achievement动态规划是一类解决多阶段决策问题的数学方法, 在工程技术、科学管理、工农业生产及军事等领域都有广泛的应用。在理论上,动态规划是求解这类问题全局最优解的一种有效方法,特别是对于实际中某些非线性规划问题可能是最优解的唯一方法。然而,动态规划仅仅决多阶段决策问题的一种方法,或者说是考查问题的一种途径,而不是一种具体的算法。就目前而言,动态规划没有统一
5、的标准模型,其解法也没有标准算法,在实际应用中,需要具体问题具体分析。动态规划模型的求解问题是影响动态规划理论和方法应用的关键所在,而子问题的求解和大量结果的存储、调用更是一个难点所在。然而, 随着计算机技术的快速发展,特别是内存容量和计算速度的增加,使求解较小规模的动态规划问题成为可能,从而使得动态规划的理论和方法在实际中的应用范围迅速增加。目前,在计算机上实现动态规划的一般求解方法并不多见,尤其是用来解决较复杂的具体问题的成果甚少。本文从实际出发,利用数学工具软件 matlab 的强大功能, 对动态规划模型的求解方法做了尝试,编写出了动态规划逆序算法的 matlab 程序,并结合“生产与存
6、储问题”1 和“背包问题” 1进行了应用与检验,实际证明结果是令人满意的。1 动态规划的基本模型实际中,要构造一个标准的动态规划模型,通常需要采用以下几个步骤:划分阶段 按照问题的时间或空间特征,把问题分为若干个阶段。这些阶段必须是有序的或者是可排序的(即无后向性) ,否则,应用无效。选择状态 将问题发展到各个阶段时所处的各种客观情况用不同的状态表示,即称为状态。状态的选择要满足无后效性和可知性,即状态不仅依赖于状态的转移规律,还依赖于允许决策集合和指标函数结构。确定决策变量与状态转移方程 当过程处于某一阶段的某个状态时,可以做出不同的决策,描述决策的变量称为决策变量。在决策过程中,由一个状态
7、到另一个状态的演变过程称为状态转移。状态转移就是根据上一阶段的状态和决策来导出本阶段的状态。写出动态规划的基本方程 动态规划的基本方程一般根据实际问题可分为两种形式,逆序形式和顺序形式。这里只考虑逆序形式。动态规划基本方程的逆序形式为f sk k( ) = opt gv s x ( k k k( , )+f sk+1( k+1) x D sk k k( )k nn= , 1,1边界条件f sn+1( n+1) = 0 或 f s v s x n n() = n n n(,).其中第 k 阶段的状态为 sk,其决策变量 xk 表示状 sk 的决策,状态转移方程为 sk+1 =T s xk k k
8、( , ), 态处于k 阶段的允许决策集合记为 D sk k( ) , v s xk k k( ,) 为指标函数。当求解时,由边界条件从 k n= 开始 , 由后向前逆推,逐阶段求出最优决策和过程的最优值, 直到最后求出 f s1( 1) 即得到问题的最优解。动态规划逆序解法计算程序框图如下:.2 基本方程逆序算法的 matlab 程序(1)动态规划逆序求最小值的基本方程:f sk k() = x D skmin k k() gv s x( k k k( ,) +f sk+1( k+1)k nn= , 1,1边界条件 f s v s xn n( ) = n n n( , ) sk+1 =T s
9、 xk k k( , ) 。自由始端和终端的动态规划,求指标函数最小值的逆序算法递归计算程序:functionp_opt,fval=dynprog(x,DecisFun,SubObjFu n,TransFun,ObjFun)% x 为状态变量,一列代表一个阶段的状态%M_函数 DecisFun(k,x) 表示由阶段 k 的状态值 x 求出相应的允许决策集合% M_函数 SubObjFun(k,x,u)表示阶段 k 的指标函数% M_函数 TransFun(k,x,u) 是状态转移函数,其中x 是阶段 k 的状态值, u 是其决策集合% M_函数 ObjFun(v,f) 是第 k 阶段到最后阶段
10、的指标函数,当 ObjFun(v,f)=v+f 时,输入ObjFun(v,f)可以省略% 输出 p_opt 由 4 列组成,p_opt=序号组,最优轨线组,最优策略组,指标函数值组; % 输出 fval 是列向量,各元素分别表示 p_opt 各最优策略组对应始端状态 x 的最优函数值k=length(x(1,:); % k 为阶段数x_isnan=isnan(x); t_vubm=inf*ones(size(x); %t_vubm 为指标函数值的上限f_opt=nan*ones(size(x);% f_opt 为不同阶段、状态下的最优值矩阵,初值为非数 d_opt=f_opt; % d_opt
11、 为不同阶段不同状态下的决策矩阵,初值为非数tmp1=find(x_isnan(:,k); % 找出第 k 阶段状态值(不是非数)的下标tmp2=length(tmp1); for i=1:tmp2u=feval(DecisFun,k,x(tmp1(i),k);% 求出相应的允许决策向量 tmp3=length(u);for j=1:tmp3 % 该 for 语句是为了求出相应的最有函数值以及最优决策tmp=feval(SubObjFun,k,x(tmp1(i),k),u(j); if tmp6在第 k 时期末库存量为 vk+1 时的存储费为:h vk k( ) = 0.5*(v x dk +
12、 k k) 故第 k 时期内的总成本为: c x h vk k( ) + k k( ) 则阶段指标函数为:V v c x h vk k() = k k( ) + k k( )最优值函数 f Vk k() 表示从第 k 阶段初始库存量为Vk 时到第四阶段末库存量为 0 时的最小总费用。则有递推关系式:f vk k() = max(0,dk vk xkmin ) 6(V vk k() +f vk+1( k+1)f v5 ( 5 ) = 0, x d v4 = 44其中 xk max(0,d vk k),这是因为一方面每阶段生产的下限为 0;另一方面由于要保证供应,故第 k 阶段.末的库存量 vk+
13、1 必须非负,即 v x dk + k k 0 ,所以 x d v k k k。v k 的取值范围为0, min(d m dj, k) ,其中 v1 = 0,v5 = 0 。j k=为求出该问题的最优值,利用上面的计算程序 dynprog.m。根据上面所述的阶段指标函数、状态转移函数和递推关系式,编写出下面 3 个 M_函数,以备主程序调用。% DecisFun.m function u=DecisFun(k,x) d=2 3 2 4;m=6; if k=4 u=d(k)-x;else u=max(0,d(k)-x):m; End% SubObjFun.mfunction f=SubObjFu
14、n(k,x,u) d=2 3 2 4; if u=0 f=0.5*(x+u-d(k);else if u6f=106;else f=3+u+0.5*(x+u-d(k); endEnd % TransFun.m function s=TransFun(k,x,u)d=2 3 2 4;s=x+u-d(k);在 matlab 命令空间输入:x1=0:4;s=nan*ones(5,1);s(1)=0;x=s x1 x1 x1;p_opt,fval=dynprog(x,DecisFun,SubObjFun,TransFun)运行结果如下:p_opt =1.0000 0 5.0000 9.50002.00
15、00 3.0000 0 03.0000 0 6.0000 11.00004.0000 fval =20.50004.0000 0 0从上面的结果可知,每个时期的最优决策为:X1=5,x2=0,x3=6,x4=0。其相应的最小总成本为 20.5 千元。从上面的结果中还可以看出,各个时期初的库存量分别为:V1=0,v2=2,v3=0,v4=4这里的结果与文1的结果完全符合,这说明该程序是可行的。3.2 二维背包问题有一个人带一个背包上山,其可携带物品重量的限度为 10 公斤,背包体积限制为 22 立方米。假设有 3 种物品可供他选择装入背包。已知第 i 种物品每件重量为w(i)公斤,体积为 v(i
16、)立方米,携带该物品 xi 件产生的效益值为 c(i)*xi。问此人该如何选择携带物品,才能使产生的效益值最大。其中 w=3 4 5;v=8 6 4;c=4 5 6; 解:用动态规划方法求解,按物品的种类数将该问题分为 3 各个阶段;si 表示用于装入第 i 种物品到第 3 种物品的总重量;ti 表示用于装入第 i 种物品到第 3 种物品的总体积; ui 表示装入第 i 种物品的件数;可得状态转移方程:sk+1 = s ck u tk( )* k k, +1 = t ck uk( )* k允许决策集合为:s tk , k )Ds u( k k,) = uk | 0 ukmin(w vk k最优
17、值函数 f s tk k k( , ) 表示当总重量不超过sk 公斤,总体积不超过 tk 立方米背包装入第 t 种物品到第 3 种物品产生的最大效益值。可得基本方程:f s tk k k( ,) =u D s tkmaxk k k( ,)( ( )*ck u f s tk+ k+1( k+1, k+1),f v t4 ( 4 , 4 ) = 0 k= 3,2,1下面同样用计算程序 dynprog1.m 求解:在使用此程序先要建立下面 3 个 M_函数:% DecisFun1.m functionu1,u2=DecisFun1(k,x1,x2) w=3 4 5;v=8 6 4;u1=0:1:mi
18、n(x1/w(k),x2/v(k);u2=1;% 因为这里只有一个决策变量,故令 u2 恒为1,这样是程序的需要,% 也可减少计算量,此时 u2 就没有任何意义,只是一个虚拟的量% SubObjFun1.m functionf=SubObjFun1(k,x1,x2,u1,u2) c=4 5 6;f=-c(k)*u1; % 求最大值转化为求最小值.% TransFun1.m functions=TransFun1(k,x1,x2,u1,u2) w=3 4 5;v=8 6 4;s(1)=x1-u1*w(k);s(2)=x2-u1*v(k);在 matlab 命令空间输入:a1=0:10;b1=0:
19、22;s1=nan*ones(11,1);s1(1)=10; s2=nan*ones(23,1);s2(1)=22;x1=s1 a1 a1;x2=s2 b1 b1;p_opt,fval=dynprog1(x1,x2,DecisFun1,S ubObjFun1,TransFun1)运行结果如下: p_opt =1 10 22 2 1 -82 4 6 1 1 -53 0 0 0 1 0 fval =-13从 上面 的结 果可 知: 最优 装入 方案 为: u1=2,u2=1,u3=0;也即各种物品分别装入 2 件,1 件,0件,此时产生的最大效益值为 13。此程序得出的结果与事实相符合,说明此程序
20、是可行的。4 程序使用的几点说明程序 dynprog.m 只能使用于具体问题中只有一个状态变量的情形,程序 dynprog1.m 适用于状态变量为二维的情形。这两个程序都要求各阶段状态变量的取值是离散的。要使用好这两个程序,关键要做到以下三点:一、 要掌握动态规划的基本原理与基本概念,能对具体问题写出基本方程的逆序形式,要认真读懂这两个程序,理解程序中每个变量所代表的含义,只有理解了程序,才能更好地使用程序,才能对运行出的结果进行分析;二、 对具体问题要作具体的分析,要用动态规划的方法求解问题,要能够写出状态转移方程、基本方程以及允许决策集合,并要根据这些方程在 matlabruan软件中建立
21、四个 M_函数,以备主程序调用;三、 每个阶段的状态变量的取值一定要合理地离散化。5 结束语本文中运用 matlab 语言实现了动态规划(包括状态变量二维情形)的逆序算法,两个实例的应用检验了该程序的有效性,同时也表明了该算法程序对众多类典型的动态规划应用问题尤其是确定离散型的应用问题的通用性。本文拓展了文2中有关动态规划逆序算法的 matlab 程序实现,由原来的一维情形扩展到二维情形,这是一个进步。当问题的阶段数和各阶段的状态数较小时,这两个程序能够运行出结果,但当问题的阶段数较和各阶段的状态数较大时,这两个程序运行时就要花费较长的时间,有时甚至是运行不出结果来,因为花费的时间太长。参考文献:1运筹学教材编写组,运筹学M 北京:清华大学出版社,2005.62 胡良剑 丁晓东 孙晓君,数学实验-使用 MATLABM 上海:上海科技出版社,20013 张志涌,精通 MATLAB6.5M 北京:北京航空航天大学出版社,20034 刘保柱 苏彦华 张宏林, MATLAB7.0 从入门到精通(修订版) 北京:人民邮电出版社,2010