参考了两篇华为杯2019F题的优秀论文。
Gurobi软件+规划模型:https://github.com/qssxbhxy/2019GMCM
Dijkstra+蚁群算法:https://max.book118.com/html/2021/0910/7014030133004002.shtm
本篇文章建模思路参考第一篇,第二篇只是作为建模思路提了一下。建议配合第一篇参考的论文来读这篇文章。
题目:多约束条件下智能飞行器航迹快速规划
背景:飞行器在飞行的时候不能对自身精准定位,所以在飞行过程中需要误差矫正才不会偏离航线。
飞行时候的约束条件:
总结:飞行器要从A点飞到B点,中途要经过很多误差矫正点来保证航线不偏离。每个矫正点有矫正条件,要求垂直和水平误差不超过多少,同时垂直/水平矫正点只能矫正垂直/水平误差。飞行器在飞行的时候,不能立马转弯。
第一问:
针对附件1和附件2中的数据分别规划满足约束条件时飞行器的航迹,并且综合考虑以下优化目标(目标):
(A)航迹长度尽可能小;(B)经过校正区域进行校正的次数尽可能少。
并讨论算法的有效性和复杂度。
其中附件1数据的参数为: α 1 = 25 , α 2 = 15 , β 1 = 20 , β 2 = 25 , θ = 30 , δ = 0.001 \alpha_1=25,\alpha_2=15,\beta_1=20,\beta_2=25,\theta=30,\delta=0.001 α1=25,α2=15,β1=20,β2=25,θ=30,δ=0.001
附件2中数据的参数为: α 1 = 20 , α 2 = 10 , β 1 = 15 , β 2 = 20 , θ = 20 , δ = 0.001 \alpha_1=20,\alpha_2=10,\beta_1=15,\beta_2=20,\theta=20,\delta=0.001 α1=20,α2=10,β1=15,β2=20,θ=20,δ=0.001
请绘出两个数据集的航迹规划路径,并将结果(即飞行器从起点出发经过的误差校正点编号及校正前误差)依次填入航迹规划结果表,放于正文中,同时将两个数据集的结果填入附件3的Sheet1和Sheet2中。
附件1和附件2(样式):
编号,X坐标(单位: m),Y坐标(单位:m),Z坐标(单位: m),校正点类型(1表示垂直误差校正点,0表示水平误差校正点,第一个是A点,最后一个是B点)。
航迹规划结果表(样式):
校正点编号 | 校正前垂直误差 | 校正前水平误差 | 校正点类型 |
---|---|---|---|
0 | 0 | 0 | 出发点A |
N 1 N_1 N1 | ** | ||
N 2 N_2 N2 | ** | ||
… | … | … | … |
N n N_n Nn | 终点B |
解析题目:
做到这一步,其实就知道题目要我们干什么了,也知道具体的要求是什么了。
如何思考:在选题的时候,其实就应该判断出来,例如有些题目会直接写什么的优化。这题从题目上看,就能看出来和图论有关,而图论是优化题中的一种。
判断题目类型:这是优化中的图论问题。
之前是写ACM算法,很多问题都抽象好了问题和数据,但是数学建模是把实际问题抽象为数学问题,需要自己补全抽象的这一部分信息。
如何思考:在自己思考的理想状态下,思考和现实中情况的区别,并在假设的时候把这个理想状态说明清楚。既然要抽象为图论问题,那么肯定是不考虑飞行器的大小的,把飞行器当成一个质点来考虑。飞行路径既然可以按照时间乘以路径的直线来算,那么在飞行每两个点之间肯定是匀速直线,意味着也没有也没有障碍物。路径长度尽可能小,意味着在到达一个矫正点就拐弯直接去下一个矫正点,需要忽略转弯引起的轨迹变化。
模型假设:为了便于问题的研究,对题目中某些条件进行简化以及合理的假设。
如何思考:
数据分布:画出附件1和附件2的三维散点图,可以发现是个稠密图,A和B分别在图的两端,所以所有点基本都是有可能用上的,不能人为的“剪枝”。
构建邻接距离矩阵:数据一共有n个点(A点、B点、矫正点),那么需要用一个 n × n 矩阵的形式来表示各个顶点间的邻接关系。把这些点抽象成图中顶点,它们之间路径长为顶点之间边的权重,飞行器最短航线就等于求这个图的最短路。
剪枝优化:题目中有个约束条件,矫正点需要满足误差条件才能矫正,飞行器需要满足误差条件才不会偏离航线。根据这两个条件可以把邻接矩阵中不满足条件的路径剔除。
最终的邻接距离矩阵: S = ( s i j ) n × n S=(s_{ij})_{n×n} S=(sij)n×n,其中n为矫正点数加2,因为还有个A点和B点。
s i j = { 实际距离 , 起点 o r 矫正点 c i 到终点 o r 矫正点 c j , i ≠ j + ∞ , 未从起点 o r 矫正点 c i 到终点 o r 矫正点 c j s_{ij}= \begin{cases} 实际距离, 起点or矫正点c_i到终点or矫正点c_j,i\neq j \\ +\infty, 未从起点or矫正点c_i到终点or矫正点c_j \end{cases} sij={实际距离,起点or矫正点ci到终点or矫正点cj,i=j+∞,未从起点or矫正点ci到终点or矫正点cj
因为自身顶点不能相连,所以 i ≠ j i\neq j i=j。矩阵里面的值“ + ∞ +\infty +∞”表示两个点之间没有直接路径,“实际距离”表示两个点之间有直接路径。其中 s i j s_{ij} sij可以表示飞行器飞行中网络图的边的权重。
题目目标:飞行器在从起点 A 到终点 B 飞行过程中需要满足飞行路程最短的同时,尽可能经过少的飞行误差校正节点。
如何思考:
在遇到一道题前,应该先想想最暴力的方法是什么?那肯定是把所有能从A到B的路径都找出来,然后都比较一遍取出比较。比较的思路有两种,一种比较的时候可以是优先路径最短,另一种是优先矫正点最少。可以把两个思路下的都求出来做对比,选择最能够型能够兼顾航迹长度和校正点个数。但是暴力的话,题目中的数据很多,例如附件一610个矫正点,如果图矫正点之间全连结,复杂度是 O ( n n ) O(n^n) O(nn),比赛期间估计根本算不完。
如果是在比赛中可以先去搜索看看有什么相关的论文作为参考,因为这次这个比赛已经结束了,我就直接看了两篇优秀论文为参考。这是一个多目标规划问题,要同时兼顾路径尽可能短和经过矫正点尽可能少。目前看了两个优秀论文,一个思路是分别求单个目标最优,用Dijkstra求最短路径,用蚁群算法求最少矫正点,然后两个结果对比一下。另一个是合到,把最短路径和最少矫正点的目标函数放在一起,然后通过调参来求解。
本文章思路以第二种为参考,该思路的优秀论文和程序在github有公开,链接:https://github.com/qssxbhxy/2019GMCM。
航迹规划模型建立:
飞行器在飞行过程中,经过矫正点 c i c_i ci到矫正点 c j c_j cj,表示选中飞行网络图中 s i j s_{ij} sij加入最优飞行路径中,否则不加入。所以航迹规划问题可以转化为0-1整数规划问题,就是矫正点在最优飞行路径中要么选要么不选。
因此,最短路的目标函数:
m i n ∑ ( i , j ) ∈ E s i j x i j ( x i j 表示 0 和 1 ) min\sum_{(i,j)\in E}s_{ij}x_{ij}(x_{ij}表示0和1) min(i,j)∈E∑sijxij(xij表示0和1)
约束条件:
由于目标不但要路径尽可能小,还要路径点最少,可以在最短路径目标函数基础上加入路径点数的惩罚项来约束。因此,最终的目标函数为:
m i n ∑ ( i , j ) ∈ E s i j x i j + K ∑ ( i , j ) ∈ E x i j min\sum_{(i,j)\in E}s_{ij}x_{ij}+K\sum_{(i,j)\in E}x_{ij} min(i,j)∈E∑sijxij+K(i,j)∈E∑xij
K为惩罚系数。
航迹规划模型:(目标函数+约束条件)
m i n ∑ ( i , j ) ∈ E s i j x i j + K ∑ ( i , j ) ∈ E x i j min\sum_{(i,j)\in E}s_{ij}x_{ij}+K\sum_{(i,j)\in E}x_{ij} min(i,j)∈E∑sijxij+K(i,j)∈E∑xij
s . t . { ∑ ( i , j ) ∈ E x i j = ∑ ( j , k ) ∈ E x j k , ∀ j ≠ A , B ∑ ( A , j ) ∈ E x A j = 1 , ∑ ( j , A ) ∈ E x j A = 0 ∑ ( j , B ) ∈ E x j B = 1 , ∑ ( B , j ) ∈ E x B j = 0 I i h i + δ s i j − h j ⩽ ( 1 − x i j ) M ( 1 − I i ) v i + δ s i j − v j ⩽ ( 1 − x i j ) M v i ⩽ α 1 , h i ⩽ α 2 , i ∈ V v i ⩽ β 1 , h i ⩽ β 2 , i ∈ H s.t. \begin{cases} \sum_{(i,j)\in E}x_{ij}=\sum_{(j,k)\in E}x_{jk},\forall j\not=A,B \\ \sum_{(A,j)\in E}x_{Aj}=1,\sum_{(j,A)\in E}x_{jA}=0 \\ \sum_{(j,B)\in E}x_{jB}=1,\sum_{(B,j)\in E}x_{Bj}=0 \\ I_i h_i+\delta s_{ij} -h_j \leqslant (1-x_{ij})M \\ (1-I_i )v_i+\delta s_{ij} -v_j \leqslant (1-x_{ij})M \\ v_i \leqslant \alpha_1,h_i \leqslant \alpha_2,i\in V \\ v_i \leqslant \beta_1,h_i \leqslant \beta_2,i\in H \end{cases} s.t.⎩ ⎨ ⎧∑(i,j)∈Exij=∑(j,k)∈Exjk,∀j=A,B∑(A,j)∈ExAj=1,∑(j,A)∈ExjA=0∑(j,B)∈ExjB=1,∑(B,j)∈ExBj=0Iihi+δsij−hj⩽(1−xij)M(1−Ii)vi+δsij−vj⩽(1−xij)Mvi⩽α1,hi⩽α2,i∈Vvi⩽β1,hi⩽β2,i∈H
如何思考:前面模型建立是把目标函数和约束用数学的语言表达出来,这一步则是把具体如何去求解前面的模型过程解释出来,要用一些具体实际计算出来的数值作为说明。
先说数据预处理,数据量有多大、处理之后有多大、具体如何处理的。
模型和算法的具体实现,除了用语言描述,还可以用step1、step2…stepn或者
流程图描述。如果是用了现成的库,可以把用了什么厂商的库说一下。
模型和算法具体运行的情况,迭代了多少次、花了多少时间、不同调参下的数据结果、如何选择出最好的结果。这里可以用一些图和表辅助论文的表达。
下面具体举例,以前面模型建立的文章的数据为主。
数据预处理:前面模型建立提到了数据处理,会对邻接距离矩阵进行剪枝。没做剪枝处理前,附件1的边数为374544。附件1中,假设飞行器从i点飞到j点,满足j属于垂直矫正点,那么 δ s i j ⩽ min { α 1 , α 2 } \delta s_{ij} \leqslant \min\{\alpha_1,\alpha_2\} δsij⩽min{α1,α2};满足j属于水平矫正点,那么 δ s i j ⩽ min { β 1 , β 2 } \delta s_{ij} \leqslant \min\{\beta_1,\beta_2\} δsij⩽min{β1,β2}。通过计算附件1,垂直矫正点边长不能超过15000m,水平矫正点长度不能超过20000m。同时到达终点的时候,垂直和水平误差都要小于 θ = 30 \theta=30 θ=30,也就是到达终点边长不能超过30000m。剪枝后,附件1中的边数降为31266。可以看出来,“剪枝”处理数据大大减少了边长数量,从而加快了模型的求解。
解释:通过前面这段对附件1数据处理的内容,可以看得出来其实就是模型建立中的数据处理部分,具体处理又说了一边,然后拿出实际处理中具体的数据。
模型的实现:数据预处理后,把附件1剪枝后的数据,带入模型,利用Python调用Gurobi优化软件进行求解。调参,发现惩罚系数K取0和10000的时候,K取0表示距离优先,K取10000表示顶点个数优先。
K | 矫正点数 | 路径长度 |
---|---|---|
10000 | 8 | 104861 |
0 | 9 | 103517 |
路径长度差别不大,取K为10000的时候,能够同时兼顾矫正点数和路径长度。
解释:说一下用了什么东西完成的,Python+Gurobi;如何完成的,把预处理后的数据放入模型,然后调参,发现K取10000最好。
模型运行的情况:附件1求解,总共求解时间为15.11秒。
解释:运行用了多少时间,训练多少轮次,程序迭代多少次什么都可以写,最好有程序具体截图。
题目要求:附件1和附件2对应的航迹规划结果表,算法的有效性和复杂度分析。
如何思考:回顾一下前面题目分析中,分析出来题目要求我们要回答的是什么,也就是题目要求。一个是两个附件对应的航迹规划结果表,以及算法的有效性和复杂度分析。根据模型求解出来数据,按照航迹规划结果表格式要求,把结果放在论文中。算法的有效性指的是算法的每一个步骤都应当能有效地执行,并得到确定的结果。这个应该有个明确的答案结果就可以了。复杂度分析,一个是空间复杂度,一个时间复杂度。把剪枝前后的空间规模都说一下,然后时间复杂度说一下,最后说一下总体用时。最后还可以加个总结作为结尾。