动态规划在地下水资源系统中的应用

动态规划在地下水资源系统中的应用,第1张

地下水系统模拟与管理问题就是在充分掌握和预知地下水系统的空间结构、埋藏条件以及各种影响和控制其行为规律的自然和人为因素的前提下,进而对其进行科学的、定量的模拟与预测、管理和调控,使其向着人们所期望的目标发展和演化。地下水系统的行为规律又取决于与其关联的外部环境和系统内部参数的时、空变化规律。在地下水资源开采过程中,这些外部环境和内部参数都会发生变化,所以需要进行动态规划与管理。

狭义的动态是指时间过程,如地下水的水位、水量、水质随时间的变化等。故动态规划就是指在地下水开采的过程中,依次采取一系列的决策,以实现整个过程的最优化问题。而对于时间过程不明显或没有时间过程的所谓静态问题,如水资源分配、投资分配、最优线路等,在一定条件下,只要依据时间特点,把过程分为若干阶段,在静态模型中人为地引进时间因素,当作多阶段决策过程来考虑,同样可用动态规划的原理来研究。所以,动态规划实质上是将一个较复杂的过程最优化决策问题,转化为多阶段的一系列简单静态问题来求解[117]。

近年来,我国许多学者研究了动态规划在水资源系统中的优化问题。方乐润等[118]建立了地下水资源系统的动态规划模型,并应用于内蒙古余粮堡灌域地下水的多年调节计算;李树文等[慎档119]借助动态规划理论,分析了地表水与地下水统筹管理的多阶段决策问题,考虑到水资源系统的动态属性和系统属性,在建立水资源管理模型时,兼顾了地表水和地下水两类资源,同时分析了它们的多阶段开发问题,增强了模型的应用效果;唐德善[120]应用大系统分解协调法建立地区水资源优化分配数学模型,以递阶动态规划法阐明了求解地区水资源优化分配数学模型的思路,并以实例说明了模型的求解过程;王柏明、向速林等[121,122]以动态规划理论为依据,介绍了动态规划在水资源优化配置中的应用实例。

在此以潜水含水层中两单元稳定抽水量的最优分配问题为例,探讨动态规划在地下水管理中的应用。

假设有一矩形均质潜水含水层,三面为隔水边界,一面傍河,河水可视为定水头边界(图4.1)。地下水接受大气降水补给,向河流排泄,已知含水层的长2L、宽B分别为20000m和10000m,导水系数为3.6×106m2/a,降水入渗系数为0.36m/a。含水层分为两个单元,单元1、2的单位流量抽水费用分别为0.2元/m3/a和0.1元/m3/a。现规划要求对单元1和单元2的稳定抽水流量Q1、Q2进行最优分配,使其在满足总需水量45×106m3/a和两单元的稳定水位分别不低启腔于允许最低水位2.5m和5.0m的条件下,总抽水费用最小。

图4.1 矩形潜水含水层

4.1.4.1 线性规划管理模型

应用嵌入法构建的管理模型为:

目标函数:minZ=0.1Q1+0.2Q2(4.1)

约束条件:

含有协变量的地下水动态规划管理模型研究

本例应用Lingo软件求解,经过6次迭代,得到最优解计算结果(表4.1)。

表4.1 嵌入法的计算结果

4.1.4.2 动态规划求解

本例采用动态规划顺序递推法求解。分两个阶段,即k=1,2。决策变量为Q1和Q2,状态变量u1,u2,u3分别表示从第1阶段到第2阶段中第一约束至第三约束可供分配的右端数值。应用状态转移方程法把水位约束用水量约束表示出来。并取水量单位为106m3/a,费用单位为106元/a。则模型如下:

目标函数:

约束条件:

含有协变量的地下水动态规划管理模型研究

此管理模型的求解过程如下:

(1)当k=1时,有:

含有协变量的地下水动态规划管理模型研究

相应地有Q1=u3-Q2,因为u3=45,故Q1=45-Q2。

(2)求出Q2的取值范围。由Q1=45-Q2和其他约束条件一起求出Q2的取值范围是0≤Q2≤36.5。

(3)当k=2时,由最优化原则,有:

含有协变量的地下水动态规划管理模型研究

相应地有Q2=0m3/a,则Q1=45-Q2=45×106m3/a,总抽水费用最小值为4.5×106元/a。

由规划结果可以看出,线性规划与动态规划计算结果一致。这说明动态规划法对于解决多阶段决策过程最优化问题,是比较有效的,其关键在于如何恰当地确定多阶段问题的动态规划数学模型和递推方程[121]。

4.1.4.3 动态规划的不足之处及改进方法

动态规划对于研究地下水资源最优分配问题,特别是对缺水地区的水资源进行规划利用和管理,使有限的地下水资源获得宽旁乱合理的经济效益,具有重要的意义。应当指出:尽管动态规划法适用于求解各种各样的多阶段决策问题,但是并非所有的此类问题都能用动态规划法求得最优解。由于动态规划法本身固有的一些弱点,限制了它在地下水管理中的一些应用。

动态规划的不足之处主要有以下两点:首先,到目前为止没有一个统一的标准模型可供应用,由于实际问题不同,其动态规划模型也就有异;其次,该方法存在多状态决策的“维数灾”问题,极大地限制了动态规划的应用。实践表明,当状态变量个数多于四时,一般动态规划方法求解的计算工作量大得惊人,即使应用现代高速大容量电子计算机也难于胜任[123]。因为随着状态变量数目(维数)的增加,每个阶段需要检验的状态组合数和计算工作量将按指数规律急剧增加。近年来针对一般动态规划的维数灾问题,不少学者做了大量的研究工作,提出了以下改进方法:

(1)逐次优化算法(Progressive Optimality Algorithm,POA):Howson和Saneho于1975年提出POA,用来解决凸性约束条件下多阶段决策问题[124]。该方法的优点是不需要对状态变量进行离散化,能够得到全局最优解,但是需要大量计算时间。多用于水库优化调度、水库群防洪调度、梯级电站经济运行等问题。

(2)双状态动态规划算法(Binary State Dynamic Programming,BSDP):Ozden M于1984年提出BSDP,用来解决四个水库优化调度问题[125]。该方法的显著特点在于构造状态子空间的一些特殊规则,是解决动态规划“维数灾”问题的一种有效方法。国内学者对BSDP做了多方面的深入研究[126],如迭代收敛条件,避免陷入局部最优解的算法,库群步长选取等。

(3)微分动态规划方法(Differential Dynamic Programming,DDP):DDP能解决多维动态规划最优管理问题。该方法逐次向预定目标逼近,与常规动态规划法相比,大大减少了计算工作量和计算机的存贮量。不足之处在于程序设计较为复杂。在求解水资源(包括地下水和地表水库)动态规划管理模型中,目前用得较普遍的方法是微分动态规划。

除上述改进方法外,还有增量动态规划法、状态增量动态规划法、单增量搜索解法、有后效性动态规划逐次逼近法、线性-动态规划算法、随机动态规划、模糊动态规划法等,在此不再详述。

蒙特卡洛: 大量随机抽样下的比对,最后结果就是在当前抽样数量下筛选出的一定是最想要的那个结果。举例:假如篮子里有1000个苹果(你定的测试集),让你 每次闭着眼睛找一个最大的,可以不限制挑选次数;于是,你可以闭着眼随机拿了一个,然后再随机拿一个与第一个比,留下大的;再随机拿一个,与前次留下的比较,又 可以留下大的;循环往复这样:拿的次数越多,挑出最大苹果的可能性也就越大!但除非你把1000个苹果都挑一遍,否则你无法肯定最终挑出来的就是最大的一个。如果有 10000个苹果的话,继续如此说不定就能找到更大的!

模拟退火 :“渐渐”清楚自己的目标是什么!并不断朝“越发”明确的目标迈进,“越来越”不被诱惑干扰。举例:为了找出地球上最高的山,一只兔子在开始并没有 合适的策略,它随机地跳了很长时间!在这期间,它可能走向高处,也可能踏入平地或沟壑世姿含。但册枯是,随着时间的流逝,它“渐渐清醒”! 并“直直地”朝着最高的方向跳去, 最后就到达了珠穆朗玛峰。

粒子群 :信息的社会共享,以一个团队的形式来搜索!团队里成员信息共享,共同进步;避免一个人工作时出现目光短浅,没有全局意识。举例:就像下围棋,只 专注于搜笑一个角落的战斗不一定能获取最终的胜利,只有放眼全局,把所有己方的棋子都盘活,相互间彼此帮助,才能获得最后胜利。

蚁群 :和粒子群算法有些相似,都是靠团队的力量共同去找目标!蚁群算法中特殊的是它的"信息素"挥发! 这个效果是其他算法中没有的!

以上所有的最优化算法都很难做到极高的精度,这是必然的: 一是 因为全局搜索已经耗费了大量的时间和资源,再过分强调精度有些不经济; 二是 因为全局搜索得到的最值可以理解为一精确最值的一个准确范围!即进入这个范围再进行精确的搜索一定可以找到精确最值;但是,全局最优的核心是随机/概率,当进入一个准确范围时,这个范围肯定是很小的,如果之后精确搜索还用全局搜索的概率参数(此时来说波动范围太大了),很可能又会跳出这个好不容易找到的精确区域!

因此: 全局最优算法与局部最优算法是要相结合的 !全局最优算法负责划定最值所在的一个精确的、较小的范围内,即告诉局部最优算法在这个范围内继续找一定可以找到精确解;局部最优算法按照较小的步长、较高的精度继续搜索精确最值。

常用全局最优算法:蒙特卡洛(MC)、模拟退火(SA)、粒子群(PSO)、蚁群(AG);

常用局部最优算法:梯度下降法、牛顿法、阻尼牛顿法、共轭梯度法;

推荐搭配1:蒙特卡洛

推荐搭配2:粒子群 + 梯度下降

推荐搭配3:蚁群 + 梯度下降 + 重检机制

以上提到算法的 “程序 + 详细使用说明” 参考以下地址:

优化算法

函数详见rres,此代码使该算法运行了两次

收获:

这是我第一个实现的代码。学习完该算法以后,逻辑框架基本上就有了,剩下需要明确的就是对应的python的语言。于是我启弊就开始了查找“如何定义函数”(详见mofan的优酷),“循环体”和“if条件语句”的格式(https://blog.csdn.net/qq_39407518/article/details/79822498)“数学符号”(详见mofan的优酷),以及print的使用

1.def是python中指定义,一般用来定义函数,如果需要深度学习搭建网络可用来定义网络。值得注意的一点是

我不清楚为什么,但是如果没有加的话,那个函数公式就是一个花瓶,就像一个结果输不出去。

2.最坑的就是逻辑。一开始逻辑没理清楚,或者说在代码上有疏漏,导致我将left和right放在了循环体里,结果可想而知。不过也是因为这个错误,我知道pycharm中的debug怎么用,挺简单的,百度一下就出来了。

3.不知道什么原因,看的莫烦视频中的print多个变量一起输出是没有办法在我的pycharm中使用的,出来的结果很奇怪。可能是因为我是win10不是ios吧。print如果多个变量一起输出必须是print("名字:%s,名字2:%s"%(a,b))结果输出就是名字:a ,名字2:b

关于python中数据变量。第一遍运行结果出现很明显不对,于是我采用了debug。结果发现,mid1处一直为1而不是1.5,于是就开始了解数据变量。起初我猜测python默认所有变量为整型,但是根据二分法的结果我意识到此猜测不对,所以要改整个file的变量格式没有必要。所以我就在mid1式子前面加了一个float,结果就显示为1.5了。但是如果我将整个式子用()括起来,前面加float,结果还是1。我不太理解为什么。不过我知道了python的数据格式是根据输入量决定的,也就是说你的输入量如果是整型,那么与其直接相关的计算输出结果一定是整型,而且还是不采用进位的整型。在我没有采用+float/+.0这两种方法之前,mid1~3全部是整型。

或者不再mid1前面加float,直接将输入量后面点个点就行

真的很想吐槽一下print,好麻烦啊啊啊啊每次都得弄个%s,而且有时候还不能放一起!!!!

不要问我掌握了什么,要问我现在写完这个代码后有清指多么的爱python的精度表示 :-)我决定以后只要再编写数学公式的代码都将输入量的小数学点后面补很多0

fibonacci函数定义,每次debug后我的手都是抖的O( _ )O~

不知道自己什么时候有的强迫症,只要是代码下面有“~”我就必须要消掉。笑哭。这个很简单,前四个除了费波纳茨,都很简单。

这个公式看起来很麻烦,便写的时候更要谨慎。我上回把那个2搁在了分号下面,结果很大,所以还是换算成0.5更好(PS:勿忘那长河般的0)。

虽然代码很长,但是主要是因为print太多。本打算在开头print,最后结果会漏掉最后一部分。懒得想其他办法了,直接就这样吧

一开始while里面写成了>,导致run不出来。继而,debug也没法用。在网上一查才知道 “没联网”+“没选断点”。最后想尝试将else里面的内容输出来,结果发现run以后被刷屏了。于是改成i<7以后还是不行,于是想着加一个break跳出循环,结果成效了。

然后刚刚由debug了一下,才知道答旁配原来是i+1在if里面,因为没有办法+1,所以i=6一直存在,就不断循环。因为加break也好,i+1也好,都可以。

这是我第一组自己实现的python代码,就是数学公式用python语言组装起来。刚开始的时候知道大概需要在语言中体现什么,但不太清楚。于是我就在网上找了几个二分法的,他们都各有不同,但框架都差不多,不过如果要用到我们的那个公式里还需要改变很多。然后我就开始分析我们的题,我发现大体需要两部分,一部分函数定义,一部分循环体。但我不知道如何定义函数,如何写数学公式,如何弄变量,也就是说一些小点不太会,所以我选择直接百度。因为我知道自己阅读的能力不错,相比于从视频中提取要素,我更擅长通过阅读获得要点。有目的性地找知识点,掌握地更牢固。

于是我就开始了第一个——二分法的编写。我发现,自己出现了很多错误而且有很多地方都很基础。但我依然没选择视频,而是将这些问题直接在百度上找,因为视频讲完或许你也没找到点。当然,这是一步一步走的,不是直接就将程序摆上去,一点一点改。

随着前两个的成功,我发现自己对于这些代码有了自信,似乎看透了他们的伪装,抓住了本质。除此之外,我还意识到自己自从8月份以后,学习能力似乎提高了不少,而且有了更为有效的学习方法。各方面都有了一定的觉醒。除了第一个找了几个牛头不对马嘴的代码,其他都是根据自己的逻辑写,逻辑通下来以后,对应语言中某一部分不知道如何翻译就去百度,其实这几个套路都一样或者说数学公式转化的套路都一样。

我还意识到,汇编其实是最难的语言,目前为止所学到的,因为很多都需要自己去定义,去死抠,需要记住大量的指令且不能灵活变通。但是其他的却只需要将一些对应的记下来就好。python真的挺简单的。而且,我发现自己今天似乎打开了新世界的大门,我爱上了这种充满了灵性的东西,充满了严谨的美丽,还有那未知的变化,我发现我似乎爱上了代码。可能不仅仅局限于python,这些语言都充满了挑战性。我觉得当你疑惑的时候,就需要相信直觉,至少我发现它很准


欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/yw/12547766.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2023-05-26
下一篇 2023-05-26

发表评论

登录后才能评论

评论列表(0条)

保存