- 在线时间
- 538 小时
- 最后登录
- 2023-6-27
- 注册时间
- 2015-11-2
- 听众数
- 29
- 收听数
- 1
- 能力
- 0 分
- 体力
- 21642 点
- 威望
- 0 点
- 阅读权限
- 60
- 积分
- 6868
- 相册
- 0
- 日志
- 0
- 记录
- 0
- 帖子
- 749
- 主题
- 600
- 精华
- 0
- 分享
- 0
- 好友
- 10
TA的每日心情 | 奋斗 2023-5-24 09:14 |
|---|
签到天数: 119 天 [LV.6]常住居民II
 群组: 2018高中组美赛 课堂 群组: 2018国赛冲刺 群组: 2018 夏令营面授课堂 群组: 2016美赛交流群组 |
|
数学建模之Lingo基础知识与应用(二)2. 在LINGO中使用集合 LP模型一个典型的输入方式:
* I1 F }, ]- L! Z 3 h4 c) W/ A9 V; n8 t3 ~8 i0 J
1. @SUM(集合(下标):关于集合的属性的表达式)
) _4 E/ F1 [* ^; V本例中目标函数也可以等价地写成 ; L [4 r' o( B# ?" A
@SUM(QUARTERS(i): 400*RP(i) +450*OP(i) +20*INV(i) ), # n2 U$ [3 d& @
“@SUM”相当于求和符号“∑”, & H" s. o9 s& z! d6 ~
“QUARTERS(i)”相当于“iQUARTERS”的含义。
: o$ H" }3 P g: L- Z由于本例中目标函数对集合QUARTERS的所有元素(下标) 都要求和,所以可以将下标i省去。 / y; h( Q" M9 j: r
2. @FOR(集合(下标):关于集合的属性的约束关系式) 3 u9 w$ L2 Y% k4 `+ \
对冒号“:”前面的集合的每个元素(下标),冒号“:”后面的约束关系式都要成立
* d* [% |: Y7 ^, T8 ?( Z为了区别i=1和i=2,3,4,把i=1时的约束关系式单独写出,即“INV(1)=10+RP(1)+OP(1)-DEM(1);” ; 6 m: s# h% J7 l9 W6 K
而对i=2,3,4对应的约束,对下标集合的元素(下标i)增加了一个逻辑关系式“i#GT#1”(这个限制条件与集合之间有一个竖线“|”分开,称为过滤条件)。
. A8 {# l6 o; n5 b! _& `限制条件“i#GT#1”是一个逻辑表达式,意思就是i>1;“#GT#”是逻辑运算符号,意思是“大于(Greater Than的字首字母缩写)” 。
. p$ S, t3 J# U8 l$ Y& c7 _! p3 i3 p* I7 j a/ Q* @ s' f" g
2.1 LINGO模型最基本的组成要素
* [9 o4 O3 }8 S4 [* z$ X一般来说,LINGO中建立的优化模型可以由五个部分组成,或称为五“段”(SECTION): 2 s( p; k) y* U
(1)集合段(SETS):以“ SETS:” 开始, “ENDSETS”结束,定义必要的集合变量(SET)及其元素(MEMBER,含义类似于数组的下标)和属性(ATTRIBUTE,含义类似于数组)。
1 l; W% u8 g" g0 b; y7 |* b(2)目标与约束段:目标函数、约束条件等,没有段的开始和结束标记,因此实际上就是除其它四个段(都有明确的段标记)外的LINGO模型。
L2 B: h) v9 l1 A: ]& D这里一般要用到LINGO的内部函数,尤其是与集合相关的求和函数@SUM和循环函数@FOR等。
. o* [8 C5 [0 s4 n i/ J(3)数据段(DATA):以 “DATA:” 开始, “ENDDATA”结束,对集合的属性(数组)输入必要的常数数据。
% A2 J: F6 H5 _: [! {格式为:“attribute(属性) = value_list(常数列表);”
' d& ?2 p2 t' C# `* ^4 }7 j常数列表(value_list)中数据之间可以用逗号“,”分开,也可以用空格分开(回车等价于一个空格),如上面对DEM的赋值也可以写成“DEM=40 60 75 25;”。
% k$ t% @0 |3 e) a5 Q(4)初始段(INIT):以“INIT: ”开始, “ENDINIT”结束,对集合的属性(数组)定义初值(因为求解算法一般是迭代算法,所以用户如果能给出一个比较好的迭代初值,对提高算法的计算效果是有益的)。
1 y. `8 X" W" d( B% ^( v, q如果有一个接近最优解的初值,对LINGO求解模型是有帮助的。定义初值的格式为:
$ b q' _# m/ f. E3 q6 q“attribute(属性) = value_list(常数列表);” # x0 y# Q8 N: K q+ R& P; |' }
(5)计算段(CALC):以“CALC: ”开始, “ENDCALC”结束,对一些原始数据进行计算处理。 ' i$ {: M! v. a/ q
在实际问题中,输入的数据通常是原始数据,不一定能在模型中直接使用,可以在这个段对这些原始数据进行一定的“预处理”,得到模型中真正需要的数据。
( q. R# p, m/ t5 @( ?3 @9 s3 M8 T2 m% C例如上例,如果希望得到全年的总需求和季度平均需求,可以增加这个段:
+ h& \2 s; g* zCALC: T_DEM = @SUM(quarters: DEM); !总需求; A_DEM = T_DEM / @size(quarters); !平均需求;ENDCALC
9 l/ e7 @' c8 M" d; Y2.2 基本集合与派生集合 ' U5 c1 j+ Y: j* T5 d1 t" ^
( D! W) ~+ q9 Q" n8 }
$ g9 P2 ^9 F- y+ ~6 _# q
1.定义了三个集合,其中LINK在前两个集合DEMAND 和SUPPLY的基础上定义; h$ @( v4 L& O! H4 C
2.在程序开头用TITLE语句对这个模型取了一个标题“LOCATION PROBLEM;并且对目标行([OBJ])和两类约束(DEMAND_CON、SUPPLY_CON)分别进行了命名(请特别注意这里约束命名的特点)。# u& e6 A4 ?, D- E% J7 B$ O, c
3.INGO对数据是按列赋值的 * }, z1 s# Q+ E- ~
语句的实际赋值顺序是X=(5,2), Y=(1,7), 而不是X=(5,1), Y=(2,7) # ]6 n& |: V( @9 U5 B6 g5 I
等价写法:
, f7 o- N6 G$ x2 s/ j“X=5,2; Y=1,7;” : T7 b3 {8 R# P, F+ U @7 B$ f* {
解得:
+ ~4 A$ i* i9 u8 x$ |6 u2.3 稠密集合与稀疏集合
h& |" c& _; @包含了两个基本集合构成的所有二元有序对的派生集合称为稠密集合(简称稠集)。有时候,在实际问题中,一些属性(数组) 只在笛卡儿积的一个真子集合上定义,这种派生集合称为稀疏集合(简称疏集)。
$ p e/ D1 S. \. c$ G' R6 e例 (最短路问题) 在纵横交错的公路网中,货车司机希望找到一条从一个城市到另一个城市的最短路. 下图表示的是公路网, 节点表示货车可以停靠的城市,弧上的权表示两个城市之间的距离(百公里). 那么,货车从城市S出发到达城市T,如何选择行驶路线,使所经过的路程最短? ) s- Z6 g7 p' r' A- \9 x, s
?- z0 I+ ^, F* \# V
/ `3 q f& z/ e5 a此例中可把从S到T的行驶过程分成4个阶段,即 S→Ai (i=1,2或3), Ai → Bj(j=1或2), Bj → Ck(k=1或2), Ck → T. 记d(Y,X)为城市Y与城市X之间的直接距离(若这两个城市之间没有道路直接相连,则可以认为直接距离为∞),用L(X)表示城市S到城市X的最优行驶路线的路长:
) b" K7 \3 z7 q" d- X![]()
p7 P+ I( |2 l: P4 A& C$ X: Y0 ?* a6 ~6 L3 s3 A. }
![]()
3 r0 n$ h7 l$ q6 P本例的LINGO求解:
" |6 P, C) `: ]0 s7 P, _: F A* l![]()
) X; r/ `* Q9 j0 P z9 S0 u
. o! t; L5 u2 i! J! j$ m " [! o* U; G" Z$ _4 ]8 X0 o
9 p' s; ?: k* V8 \* n. N5 ~运行结果:
' p6 {1 L6 R2 o7 S2 {8 G! [2 |+ ]6 l6 b; B* s0 I/ P2 c
1.“CITIES”(城市):一个基本集合(元素通过枚举给出)
t- |3 T0 o" E' B. j0 x2.“ROADS”(道路):由CITIES导出的一个派生集合(请特别注意其用法),由于只有一部分城市之间有道路相连,所以不应该把它定义成稠密集合,将其元素通过枚举给出,这就是一个稀疏集合。
% x$ Q, y8 z0 @3.从模型中还可以看出:这个LINGO程序可以没有目标函数,这在LINGO中,可以用来找可行解(解方程组和不等式组)。+ S8 Q- u5 y' G% D9 u
2.4 集合的使用小结
! p- W' ~! @7 a0 h# E![]()
* E- K; I1 ^' E- k9 [5 y E% \+ {: _. r9 P/ Z
1. 基本集合的定义格式为(方括号“[ ]”中的内容是可选项, 可以没有): / U3 ?7 W7 N8 L' X9 t* B. T' ?
setname [/member_list/] [: attribute_list];
" G. t" X, n, l! ^其中setname为定义的集合名,member_list为元素列表,attribute_list为属性列表。元素列表可以采用显式列举法(即直接将所有元素全部列出,元素之间用逗号或空格分开),也可以采用隐式列举法。 . T% s" s3 a9 U* z3 x+ t. @. [
2. 派生集合的定义格式为(方括号“[ ]”中的内容是可选项, 可以没有): & O2 n6 O2 G6 Q0 V, }6 ]" @
setname(parent_set_list) [/member_list/] [: attribute_list];
# R4 l' {$ s/ c# U与基本集合的定义相比较多了一个parent_set_list(父集合列表)。 ) j, b4 j. K9 W- O
父集合列表中的集合(如 set1,set2,…,等)称为派生集合setname的父集合,它们本身也可以是派生集合。
7 g/ l+ l% \% F
5 E5 \' [$ k7 m) s! t% ~: e/ s2 V# L. `. D* U# u/ q
$ y. {( j- Z' a: r# u) Q$ _# D$ G* E( q' R' T- u0 J: d1 M1 `
! n# N6 H4 L1 \- u+ k6 @: F
|
zan
|