AMPL下载安装于基本使用(二)

1 带有下标的优化模型

优化问题大部分情况下,参数有很多,约束也有很多,但大部分参数和约束都是同类型的,在数学表达式中往往都以下标来区分,例如《运筹学》(罗纳德 L. 拉丁)中的Pi Hybrids问题的优化模型的数学表示:
在这里插入图片描述
注,这是来自书中的截图,这里的demands错误,d的下标应该为h,r

另一方面,为了让程序具有通用性,都是模型与数据分开的,即放在两个文件中,这样改数据的时候可以不用动模型。

我们以《运筹学》(罗纳德 L. 拉丁)中的Pi Hybrids问题为例来说明模型与数据分离时如何写程序,同时使用下标来表达多参数、多约束的模型。

2 编写模型

第一步是写模型,新建一个名为pi_hybrids.mod的模型文件,这个上节讲过怎么操作,文件内容如下:

model;		# 声明此部分为模型部分

# param定义基本符号参数:设备、品种、销售地
param l;		# l台设备
param m;		# m个玉米杂交品种
param n;		# n个销售地

# set定义序列,这里定义的是标引(下标)的取值范围
set facils := 1 .. l;	# 设备编号范围,这里facils是一个序列,类似于python中的range用法
set hybrs := 1 .. m;	# 玉米杂交品种编号范围
set regns := 1 .. n;	# 销售地编号范围

# 定义其他符号参数,这里用下标的方式,使用一条param语句同时定义一组参数
# 下面的像f、h、r这些标引,都不需要单独定义,但它们每次出现,
# 都需要使用花括号声明其范围,同一条语句只需要声明一次
param u{f in facils};		# 编号为f的设备的加工能力,即设备f处理玉米谷粒的能力											
param a{h in hybrs};		# 生产一袋h品种玉米杂交种所需的谷粒数量
param p{f in facils, h in hybrs};				# 设备f生产一袋h品种的生产成本(金钱成本)
param d{h in hybrs, r in regns};				# 销售地r对h品种的需求量
param s{f in facils, h in hybrs, r in regns};	# 从设备f,将一袋h品种玉米杂交种运输到销
												# 售地r的运输成本
												
# 定义决策变量及其类型约束,这里同样使用下标的方式,可以通过一条var语句同时定义一组决策变量
var x{f in facils, h in hybrs} >= 0;				# 使用设备f,生成品种h的袋数
var y{f in facils, h in hybrs, r in regns} >= 0;	# 从设备f,运输品种h,到销售地r的袋数

# 定义目标函数,这里sum是求和符号,通过下标定位参数或决策变量,需要通过[]
minimize tcost: sum{f in facils, h in hybrs} p[f, h]*x[f, h]
+ sum{f in facils, h in hybrs, r in regns} s[f, h, r]*y[f, h, r];

# 定义主约束,使用下标的方式,通过一条语句同时定义一组约束
subject to
fcap{f in facils}: sum{h in hybrs} a[h]*x[f, h] <= u[f];				# 设备能力约束
rdems{h in hybrs, r in regns}: sum{f in facils} y[f, h, r] = d[h, r];	# 运输等于需求
psbal{f in facils, h in hybrs}: sum{r in regns} y[f, h, r] = x[f, h];	# 运输等于生产

由于CSDN中没有AMPL代码格式,我用截图看起来能更方便一些,因为关键字有颜色:
在这里插入图片描述

我们可以归纳一下上述程序的步骤:
(1)定义基本符号参数,如l m n
(2)定义下标的范围,通过定义序列来进行;
(3)通过下标定义其他参数;
(4)定义决策变量及其类型约束;
(5)定义主约束。
这五步通常是AMPL写模型的标准流程,是层层递进的关系。

2 组织数据

在与py_hybrids.mod文件的同目录下新建一个名为py_hybrids.dat的文件,也可以是其他名字(以容易识别为准),但后缀必须是.dat,新建的时候可以在“File Extension”中选择:
在这里插入图片描述
py_hybrids.dat内容如下:

data;		# 声明此部分为模型部分

# 给没有下标的基本参数赋值
param l := 2;		# “:=”表示赋值
param m := 4;
param n := 3;

# 以列表形式,给只有单个下标的参数赋值
param u := 1 2200 2 2555;		# u[1]为2200,u[2]为2555
param a := 1 7 2 11 3 6 4 18;

# 以表格形式,给多重下标的参数赋值,为了方便观察,建议用tab隔开

# 二重下标
param p: 	1 		2 		3 		4 :=
1 			1.10 	0.89 	2.05 	1.45
2 			1.55 	1.13 	2.15 	1.56 ;

param d : 	1 		2 		3 :=
1 			123 	119 	500
2 			311 	281 	333
3 			212 	188 	424
4 			189 	201 	440 ;

# 三重下标
param s: 	1 		2 		3 :=
1	1 		0.89 	0.91 	0.77
1	2 		1.00 	0.84 	0.89
1	3 		0.77 	0.76 	0.78
1	4 		0.99 	1.03 	0.85
2	1 		0.92 	0.89 	0.92
2	2 		0.87 	0.95 	0.90
2	3 		0.91 	0.83 	0.77
2	4 		0.89 	0.79 	0.86 ;	# s[2, 4, 1]即为0.89,列标表示最后一个下标

截图看的更清晰:
在这里插入图片描述
书中还是有错的,因为p[f, h],f=1, ... , l l=2 那么f只能等于1或2,所以参数p只能有两行,但书中有4行,我删掉了后面两行,否则后面运行命令data pi_hybrids.dat;时会报错。

3 控制台运行

控制台输入如下数据:

ampl: reset;
ampl: model pi_hybrids.mod;
ampl: data pi_hybrids.dat;
ampl: option solver cplex;
ampl: solve;

结果:
在这里插入图片描述
可能是书中的数据没有组织好,导致约束无法被满足,即约束之间相互冲突,所以这里报错。当然,我们这里只是过一下案例,知道怎么操作模型与数据分离、带有下标的情况就行了,具体结果这里不重要。

相关推荐

最近更新

  1. docker php8.1+nginx base 镜像 dockerfile 配置

    2024-06-09 15:30:03       91 阅读
  2. Could not load dynamic library ‘cudart64_100.dll‘

    2024-06-09 15:30:03       97 阅读
  3. 在Django里面运行非项目文件

    2024-06-09 15:30:03       78 阅读
  4. Python语言-面向对象

    2024-06-09 15:30:03       88 阅读

热门阅读

  1. 未来的视窗:苹果Vision Air猜想与期待

    2024-06-09 15:30:03       24 阅读
  2. vue3如何定义一个组件

    2024-06-09 15:30:03       29 阅读
  3. SQL Server(四)

    2024-06-09 15:30:03       28 阅读
  4. 数学学习基本理念与方法

    2024-06-09 15:30:03       28 阅读
  5. 看屏幕久了如何休息眼睛

    2024-06-09 15:30:03       27 阅读
  6. C++的算法:欧拉道路与欧拉回路

    2024-06-09 15:30:03       29 阅读
  7. C++细节梳理之模版

    2024-06-09 15:30:03       31 阅读
  8. Websocket前端与后端:深度探索与实战应用

    2024-06-09 15:30:03       27 阅读
  9. 基于springboot的欢迪迈手机商城源码数据库

    2024-06-09 15:30:03       25 阅读
  10. Python Number(数字)

    2024-06-09 15:30:03       34 阅读