欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

Python實(shí)現(xiàn)蟻群算法

 更新時(shí)間:2022年03月04日 16:04:23   作者:是夢(mèng)吧,是你吧!  
本文主要介紹了Python實(shí)現(xiàn)蟻群算法,文中通過(guò)示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下

1、引言

在自然界中各種生物群體顯現(xiàn)出來(lái)的智能近幾十年來(lái)得到了學(xué)者們的廣泛關(guān)注,學(xué)者們通過(guò)對(duì)簡(jiǎn)單生物體的群體行為進(jìn)行模擬,進(jìn)而提出了群智能算法。其中,模擬蟻群覓食過(guò)程的蟻群優(yōu)化算法(Ant Colony Optimization, ACO)和模擬鳥(niǎo)群運(yùn)動(dòng)方式的粒子群算法(Particle Swarm Optimization, PSO)是兩種最主要的群智能算法。

蟻群算法是一種源于大自然生物世界的新的仿生進(jìn)化算法,由意大利學(xué)者M(jìn). Dorigo, V. Maniezzo和A.Colorni等人于20世紀(jì)90年代初期通過(guò)模擬自然界中螞蟻集體尋徑行為而提出的一種基于種群的啟發(fā)式隨機(jī)搜索算法"。螞蟻有能力在沒(méi)有任何提示的情形下找到從巢穴到食物源的最短路徑,并且能隨環(huán)境的變化,適應(yīng)性地搜索新的路徑,產(chǎn)生新的選擇。其根本原因是螞蟻在尋找食物時(shí),能在其走過(guò)的路徑上釋放一種特殊的分泌物——信息素(也稱外激素),隨著時(shí)間的推移該物質(zhì)會(huì)逐漸揮發(fā),后來(lái)的螞蟻選擇該路徑的概率與當(dāng)時(shí)這條路徑上信息素的強(qiáng)度成正比。當(dāng)一條路徑上通過(guò)的螞蟻越來(lái)越多時(shí),其留下的信息素也越來(lái)越多,后來(lái)螞蟻選擇該路徑的概率也就越高,從而更增加了該路徑上的信息素強(qiáng)度。而強(qiáng)度大的信息素會(huì)吸引更多的螞蟻,從而形成一種正反饋機(jī)制。通過(guò)這種正反饋機(jī)制,螞蟻?zhàn)罱K可以發(fā)現(xiàn)最短路徑。

最早的蟻群算法是螞蟻系統(tǒng)(Ant System,AS),研究者們根據(jù)不同的改進(jìn)策略對(duì)螞蟻系統(tǒng)進(jìn)行改進(jìn)并開(kāi)發(fā)了不同版本的蟻群算法,并成功地應(yīng)用于優(yōu)化領(lǐng)域。用該方法求解旅行商(TSP)問(wèn)題、分配問(wèn)題、車(chē)間作業(yè)調(diào)度(job-shop)問(wèn)題,取得了較好的試驗(yàn)結(jié)果。蟻群算法具有分布式計(jì)算、無(wú)中心控制和分布式個(gè)體之間間接通信等特征,易于與其他優(yōu)化算法相結(jié)合,它通過(guò)簡(jiǎn)單個(gè)體之間的協(xié)作表現(xiàn)出了求解復(fù)雜問(wèn)題的能力,已被廣泛應(yīng)用于求解優(yōu)化問(wèn)題。蟻群算法相對(duì)而言易于實(shí)現(xiàn),且算法中并不涉及復(fù)雜的數(shù)學(xué)操作,其處理過(guò)程對(duì)計(jì)算機(jī)的軟硬件要求也不高,因此對(duì)它的研究在理論和實(shí)踐中都具有重要的意義。

目前,國(guó)內(nèi)外的許多研究者和研究機(jī)構(gòu)都開(kāi)展了對(duì)蟻群算法理論和應(yīng)用的研究,蟻群算法已成為國(guó)際計(jì)算智能領(lǐng)域關(guān)注的熱點(diǎn)課題。雖然目前蟻群算法沒(méi)有形成嚴(yán)格的理論基礎(chǔ),但其作為一種新興的進(jìn)化算法已在智能優(yōu)化等領(lǐng)域表現(xiàn)出了強(qiáng)大的生命力。

2 蟻群算法理論

蟻群算法是對(duì)自然界螞蟻的尋徑方式進(jìn)行模擬而得出的一種仿生算法。螞蟻在運(yùn)動(dòng)過(guò)程中,能夠在它所經(jīng)過(guò)的路徑上留下信息素進(jìn)行信息傳遞,而且螞蟻在運(yùn)動(dòng)過(guò)程中能夠感知這種物質(zhì),并以此來(lái)指導(dǎo)自己的運(yùn)動(dòng)方向。因此,由大量螞蟻組成的蟻群的集體行為便表現(xiàn)出一種信息正反饋現(xiàn)象:某一路徑上走過(guò)的螞蟻越多,則后來(lái)者選擇該路徑的概率就越大。

3 算法理論圖解 

(1)在自然界中,螞蟻的食物源總是隨機(jī)分散于蟻巢周?chē)?,在蟻群協(xié)調(diào)、分工、合作后總能找到一條通往食物源的最短路徑。現(xiàn)實(shí)中,我們能觀察到大量螞蟻在巢穴與食物源之間形成近乎直線的路徑,而不是曲線、圓等其他形狀,如圖(a)。

(2)螞蟻群體不僅能完成復(fù)雜的任務(wù),并且還能適應(yīng)環(huán)境的變化,如在蟻群運(yùn)動(dòng)路線上突然出現(xiàn)障礙物時(shí),一開(kāi)始各只螞蟻分布是均勻的,不管路徑長(zhǎng)短,螞蟻總是先按同等概率選擇各條路徑,如圖(b)。

(3)螞蟻在運(yùn)動(dòng)過(guò)程中,能在其經(jīng)過(guò)的路徑上留下信息素,并且能感知到這種物質(zhì)的存在及其強(qiáng)度,并以此指導(dǎo)自己運(yùn)動(dòng)的方向,螞蟻傾向于信息素濃度高的方向移動(dòng)。在相同時(shí)間內(nèi)較短路徑上的信息素量就遺留得較多,則選擇較短路徑得螞蟻也隨即增多,如圖(c)。

 

(4)不難看出,由于大量螞蟻組成得蟻群集體行為表現(xiàn)出的一種信息正反饋現(xiàn)象,在某一路徑上走過(guò)的螞蟻越多,則后來(lái)者選擇該路徑的概率就越大,螞蟻個(gè)體質(zhì)檢就是通過(guò)這種信息交流機(jī)制來(lái)搜索食物,并最終沿著最短路徑行進(jìn),如圖(d)。

4 人工蟻群優(yōu)化過(guò)程 

基于以上真實(shí)蟻群尋找食物時(shí)的最優(yōu)路徑選擇問(wèn)題,可以構(gòu)造人工蟻群,來(lái)解決最優(yōu)化問(wèn)題,如TSP問(wèn)題。人工蟻群中把具有簡(jiǎn)單功能的工作單元看作螞蟻。二者的相似之處在于都是優(yōu)先選擇信息素濃度大的路徑。較短路徑的信息素濃度高,所以能夠最終被所有螞蟻選擇,也就是最終的優(yōu)化結(jié)果。兩者的區(qū)別在于人工蟻群有一定的記憶能力,能夠記憶已經(jīng)訪問(wèn)過(guò)的節(jié)點(diǎn)。同時(shí),人工蟻群再選擇下一條路徑的時(shí)候是按一定算法規(guī)律有意識(shí)地尋找最短路徑,而不是盲目的。例如在TSP問(wèn)題中,可以預(yù)先知道當(dāng)前城市到下一個(gè)目的地的距離。

在TSP問(wèn)題的人工蟻群算法中,假設(shè)m只螞蟻在圖的相鄰節(jié)點(diǎn)間移動(dòng),從而協(xié)作異步地得到問(wèn)題的解。每只螞蟻的一步轉(zhuǎn)移概率由圖中的每條邊上的兩類參數(shù)決定:一是信息素值,也稱信息素痕跡;二是可見(jiàn)度,即先驗(yàn)值。

信息素的更新方式有兩種:一是揮發(fā),也就是所有路徑上的信息素以一定的比率減少,模擬自然蟻群的信息素隨時(shí)間揮發(fā)的過(guò)程;二是增強(qiáng),給評(píng)價(jià)值“好”(有螞蟻?zhàn)哌^(guò))的邊增加信息素。

螞蟻向下一個(gè)目標(biāo)的運(yùn)動(dòng)是通過(guò)一個(gè)隨機(jī)原則來(lái)實(shí)現(xiàn)的,也就是運(yùn)用當(dāng)前所在節(jié)點(diǎn)存儲(chǔ)的信息,計(jì)算出下一步可達(dá)節(jié)點(diǎn)的概率,并按此概率實(shí)現(xiàn)一步移動(dòng),如此往復(fù),越來(lái)越接近最優(yōu)解。

螞蟻在尋找過(guò)程中,或在找到一個(gè)解后,會(huì)評(píng)估該解或解的一部分的優(yōu)化程度,并把評(píng)價(jià)信息保存在相關(guān)連接的信息素中。

這種算法有別于傳統(tǒng)編程模式,其優(yōu)勢(shì)在于,避免了冗長(zhǎng)的編程和籌劃,程序本身是基于一定規(guī)則的隨機(jī)運(yùn)行來(lái)尋找最佳配置。也就是說(shuō),當(dāng)程序最開(kāi)始找到目標(biāo)的時(shí)候,路徑可能不是最優(yōu)的。但是,程序可以通過(guò)螞蟻尋找食物的時(shí)候的信息素原理,不斷地去修正原來(lái)的路線,使整個(gè)路線越來(lái)越短,也就是說(shuō),程序執(zhí)行的時(shí)間越長(zhǎng)(在程序中也就是迭代次數(shù)不能太少,同時(shí)還要保證一定的螞蟻數(shù)量),所獲得的路徑就越可能接近最優(yōu)路徑。這看起來(lái)很類似與我們所見(jiàn)的由無(wú)數(shù)例子進(jìn)行歸納概括形成最佳路徑的過(guò)程。實(shí)際上好似是程序的一個(gè)自我學(xué)習(xí)的過(guò)程。

這種優(yōu)化過(guò)程的本質(zhì)在于

選擇機(jī)制:信息素越多的路徑,被選擇的概率越大。

更新機(jī)制:路徑上面的信息素會(huì)隨螞蟻的經(jīng)過(guò)而增長(zhǎng),而且同時(shí)也隨時(shí)間的推移逐漸揮發(fā)消失。

協(xié)調(diào)機(jī)制:螞蟻間實(shí)際上是通過(guò)分泌物來(lái)互相通信、協(xié)同工作的。

蟻群算法正是充分利用了選擇、更新和協(xié)調(diào)的優(yōu)化機(jī)制,即通過(guò)個(gè)體之間的信息交流與相互協(xié)作最終找到最優(yōu)解,使它具有很強(qiáng)的發(fā)現(xiàn)較優(yōu)解的能力。

事實(shí)上,每只螞蟻并不是像我們想象的需要知道整個(gè)世界的信息,他們其實(shí)只關(guān)心很小范圍內(nèi)的眼前信息,而且根據(jù)這些局部信息利用幾條簡(jiǎn)單的規(guī)則進(jìn)行決策,但是,當(dāng)集群里有無(wú)數(shù)螞蟻的時(shí)候,復(fù)雜性的行為就會(huì)凸現(xiàn)出來(lái)。這就是人工生命、復(fù)雜性科學(xué)解釋的規(guī)律!那么,這些簡(jiǎn)單規(guī)則是什么呢?下面詳細(xì)說(shuō)明:

1、范圍:

螞蟻觀察到的范圍是一個(gè)方格世界,螞蟻有一個(gè)參數(shù)為速度半徑(一般是3),那么它能觀察到的范圍就是3*3個(gè)方格世界,并且能移動(dòng)的距離也在這個(gè)范圍之內(nèi)。

2、環(huán)境:

螞蟻所在的環(huán)境是一個(gè)虛擬的世界,其中有障礙物,有別的螞蟻,還有信息素,信息素有兩種,一種是找到食物的螞蟻灑下的食物信息素,一種是找到窩的螞蟻灑下的窩的信息素。每個(gè)螞蟻都僅僅能感知它范圍內(nèi)的環(huán)境信息。環(huán)境以一定的速率讓信息素消失。

3、覓食規(guī)則

在每只螞蟻能感知的范圍內(nèi)尋找是否有食物,如果有就直接過(guò)去。否則看是否有信息素,并且比較在能感知的范圍內(nèi)哪一點(diǎn)的信息素最多,這樣,它就朝信息素多的地方走,并且每只螞蟻多會(huì)以小概率犯錯(cuò)誤,從而并不是往信息素最多的點(diǎn)移動(dòng)。螞蟻找窩的規(guī)則和上面一樣,只不過(guò)它對(duì)窩的信息素做出反應(yīng),而對(duì)食物信息素沒(méi)反應(yīng)。

4、移動(dòng)規(guī)則

每只螞蟻都朝向信息素最多的方向移,并且,當(dāng)周?chē)鷽](méi)有信息素指引的時(shí)候,螞蟻會(huì)按照自己原來(lái)運(yùn)動(dòng)的方向慣性的運(yùn)動(dòng)下去,并且,在運(yùn)動(dòng)的方向有一個(gè)隨機(jī)的小的擾動(dòng)。為了防止螞蟻原地轉(zhuǎn)圈,它會(huì)記住最近剛走過(guò)了哪些點(diǎn),如果發(fā)現(xiàn)要走的下一點(diǎn)已經(jīng)在最近走過(guò)了,它就會(huì)盡量避開(kāi)。

5、避障規(guī)則:

如果螞蟻要移動(dòng)的方向有障礙物擋住,它會(huì)隨機(jī)的選擇另一個(gè)方向,并且有信息素指引的話,它會(huì)按照覓食的規(guī)則行為。

6、播撒信息素規(guī)則

每只螞蟻在剛找到食物或者窩的時(shí)候撒發(fā)的信息素最多,并隨著它走遠(yuǎn)的距離,播撒的信息素越來(lái)越少。

根據(jù)這幾條規(guī)則,螞蟻之間并沒(méi)有直接的關(guān)系,但是每只螞蟻都和環(huán)境發(fā)生交互,而通過(guò)信息素這個(gè)紐帶,實(shí)際上把各個(gè)螞蟻之間關(guān)聯(lián)起來(lái)了。比如,當(dāng)一只螞蟻找到了食物,它并沒(méi)有直接告訴其它螞蟻這兒有食物,而是向環(huán)境播撒信息素,當(dāng)其它的螞蟻經(jīng)過(guò)它附近的時(shí)候,就會(huì)感覺(jué)到信息素的存在,進(jìn)而根據(jù)信息素的指引找到了食物。

那么,螞蟻究竟是怎么找到食物的呢?

在沒(méi)有螞蟻找到食物的時(shí)候,環(huán)境沒(méi)有有用的信息素,那么螞蟻為什么會(huì)相對(duì)有效的找到食物呢?這要?dú)w功于螞蟻的移動(dòng)規(guī)則,尤其是在沒(méi)有信息素時(shí)候的移動(dòng)規(guī)則。首先,它要能盡量保持某種慣性,這樣使得螞蟻盡量向前方移動(dòng)(開(kāi)始,這個(gè)前方是隨機(jī)固定的一個(gè)方向),而不是原地?zé)o謂的打轉(zhuǎn)或者震動(dòng);其次,螞蟻要有一定的隨機(jī)性,雖然有了固定的方向,但它也不能像粒子一樣直線運(yùn)動(dòng)下去,而是有一個(gè)隨機(jī)的干擾。這樣就使得螞蟻運(yùn)動(dòng)起來(lái)具有了一定的目的性,盡量保持原來(lái)的方向,但又有新的試探,尤其當(dāng)碰到障礙物的時(shí)候它會(huì)立即改變方向,這可以看成一種選擇的過(guò)程,也就是環(huán)境的障礙物讓螞蟻的某個(gè)方向正確,而其他方向則不對(duì)。這就解釋了為什么單個(gè)螞蟻在復(fù)雜的諸如迷宮的地圖中仍然能找到隱蔽得很好的食物。當(dāng)然,在有一只螞蟻找到了食物的時(shí)候,其他螞蟻會(huì)沿著信息素很快找到食物的。

螞蟻如何找到最短路徑的?

這一是要?dú)w功于信息素,另外要?dú)w功于環(huán)境,具體說(shuō)是計(jì)算機(jī)時(shí)鐘。信息素多的地方顯然經(jīng)過(guò)這里的螞蟻會(huì)多,因而會(huì)有更多的螞蟻聚集過(guò)來(lái)。假設(shè)有兩條路從窩通向食物,開(kāi)始的時(shí)候,走這兩條路的螞蟻數(shù)量同樣多(或者較長(zhǎng)的路上螞蟻多,這也無(wú)關(guān)緊要)。當(dāng)螞蟻沿著一條路到達(dá)終點(diǎn)以后會(huì)馬上返回來(lái),這樣,短的路螞蟻來(lái)回一次的時(shí)間就短,這也意味著重復(fù)的頻率就快,因而在單位時(shí)間里走過(guò)的螞蟻數(shù)目就多,灑下的信息素自然也會(huì)多,自然會(huì)有更多的螞蟻被吸引過(guò)來(lái),從而灑下更多的信息素……;而長(zhǎng)的路正相反,因此,越來(lái)越多地螞蟻聚集到較短的路徑上來(lái),最短的路徑就近似找到了。也許有人會(huì)問(wèn)局部最短路徑和全局最短路的問(wèn)題,實(shí)際上螞蟻逐漸接近全局最短路的,為什么呢?這源于螞蟻會(huì)犯錯(cuò)誤,也就是它會(huì)按照一定的概率不往信息素高的地方走而另辟蹊徑,這可以理解為一種創(chuàng)新,這種創(chuàng)新如果能縮短路途,那么根據(jù)剛才敘述的原理,更多的螞蟻會(huì)被吸引過(guò)來(lái)。

5  基本蟻群算法及其流程 

5.1  蟻群算法公式 

蟻群算法實(shí)際上是正反饋原理和啟發(fā)式算法相結(jié)合的一種算法。在選擇路徑時(shí),螞蟻不僅利用了路徑上的信息素,而且用到了城市間距離的倒數(shù)作為啟發(fā)式因子。實(shí)驗(yàn)結(jié)果表明,ant-cycle模型比ant-quantity和ant-density模型有更好的性能。這是因?yàn)閍nt-cycle模型利用全局信息更新路徑上的信息素量,而ant-quantity和ant-density模型使用局部信息。 

5.2 蟻群算法程序概括

(1)參數(shù)初始化

在尋最短路錢(qián),需對(duì)程序各個(gè)參數(shù)進(jìn)行初始化,蟻群規(guī)模m、信息素重要程度因子α、啟發(fā)函數(shù)重要程度因子β、信息素會(huì)發(fā)因子、最大迭代次數(shù)ddcs_max,初始迭代值為ddcs=1。

(2)構(gòu)建解空間

將每只螞蟻隨機(jī)放置在不同的出發(fā)地點(diǎn),對(duì)螞蟻訪問(wèn)行為按照公式計(jì)算下一個(gè)訪問(wèn)的地點(diǎn),直到所有螞蟻訪問(wèn)完所有地點(diǎn)。

(3)更新信息素

計(jì)算每只螞蟻經(jīng)過(guò)的路徑總長(zhǎng)Lk,記錄當(dāng)前循環(huán)中的最優(yōu)路徑,同時(shí)根據(jù)公式對(duì)各個(gè)地點(diǎn)間連接路徑上的信息素濃度進(jìn)行更新。

(4)判斷終止

迭代次數(shù)達(dá)到最大值前,清空螞蟻經(jīng)過(guò)的記錄,并返回步驟2。

5.3 流程圖 

 6 案例實(shí)現(xiàn)

6.1 案例1

求解函數(shù):f(x,y)=20\times (x^{2}+y^{2})-(1-y)^{2}-3\times (1+y)^{2}+0.3的最小值,其中x的取值范圍為[-5,5], y的取值范圍為[-5, 5]。這是一個(gè)有多個(gè)局部極值的函數(shù)。

6.2 Python實(shí)現(xiàn)

import numpy as np
from tqdm import tqdm#進(jìn)度條設(shè)置
import matplotlib.pyplot as plt
import matplotlib as mpl
import matplotlib; matplotlib.use('TkAgg')
mpl.rcParams['font.sans-serif'] = ['SimHei']  # 指定默認(rèn)字體
mpl.rcParams['axes.unicode_minus'] = False  # 解決保存圖像是負(fù)號(hào)'-'顯示為方塊的問(wèn)題
 
 
#============蟻群算法求函數(shù)極值================
 
#=======適應(yīng)度函數(shù)=====
def func(x,y):
    value = 20*np.power(x*x-y*y,2)-np.power(1-y,2)-3*np.power(1+y,2)+0.3
    return value
#=======初始化參數(shù)====
m=20                   #螞蟻個(gè)數(shù)
G_max=200              #最大迭代次數(shù)
Rho=0.9                #信息素蒸發(fā)系數(shù)
P0=0.2                 #轉(zhuǎn)移概率常數(shù)
XMAX= 5               #搜索變量x最大值
XMIN= -5              #搜索變量x最小值
YMAX= 5               #搜索變量y最大值
YMIN= -5              #搜索變量y最小值
X=np.zeros(shape=(m,2)) #蟻群 shape=(20, 2)
Tau=np.zeros(shape=(m,)) #信息素
P=np.zeros(shape=(G_max,m)) #狀態(tài)轉(zhuǎn)移矩陣
fitneess_value_list=[] #迭代記錄最優(yōu)目標(biāo)函數(shù)值
#==隨機(jī)設(shè)置螞蟻初始位置==
for i in range(m):#遍歷每一個(gè)螞蟻
    X[i,0]=np.random.uniform(XMIN,XMAX,1)[0] #初始化x
    X[i,1]=np.random.uniform(YMIN,YMAX,1)[0] #初始化y
    Tau[i]=func(X[i,0],X[i,1])
 
step=0.1;                #局部搜索步長(zhǎng)
for NC in range(G_max):#遍歷每一代
    lamda=1/(NC+1)
    BestIndex=np.argmin(Tau) #最優(yōu)索引
    Tau_best=Tau[BestIndex] #最優(yōu)信息素
     #==計(jì)算狀態(tài)轉(zhuǎn)移概率===
    for i in range(m):#遍歷每一個(gè)螞蟻
        P[NC,i]=np.abs((Tau_best-Tau[i]))/np.abs(Tau_best)+0.01 #即例最優(yōu)信息素的距離
 
    #=======位置更新==========
    for i in range(m):  # 遍歷每一個(gè)螞蟻
        #===局部搜索====
        if P[NC,i]<P0:
            temp1 = X[i, 0] + (2 * np.random.random() - 1) * step * lamda # x(2 * np.random.random() - 1) 轉(zhuǎn)換到【-1,1】區(qū)間
            temp2 = X[i,1] + (2 * np.random.random() - 1) * step * lamda #y
        #===全局搜索====
        else:
            temp1 = X[i, 0] + (XMAX - XMIN) * (np.random.random() - 0.5)
            temp2 = X[i, 0] + (YMAX - YMIN) * (np.random.random() - 0.5)
 
        #=====邊界處理=====
        if temp1 < XMIN:
            temp1 =XMIN
        if temp1 > XMAX:
            temp1 =XMAX
        if temp2 < XMIN:
            temp2 =XMIN
        if temp2 > XMAX:
            temp2 =XMAX
 
 
        #==判斷螞蟻是否移動(dòng)(選更優(yōu)===
        if func(temp1, temp2) < func(X[i, 0], X[i, 1]):
            X[i, 0] = temp1
            X[i, 1]= temp2
 
    #=====更新信息素========
    for i in range(m):  # 遍歷每一個(gè)螞蟻
        Tau[i] = (1 - Rho) * Tau[i] + func(X[i, 0], X[i, 1]) #(1 - Rho) * Tau[i] 信息蒸發(fā)后保留的
        index=np.argmin(Tau)#最小值索引
        value=Tau[index]#最小值
    fitneess_value_list.append(func(X[index,0],X[index,1])) #記錄最優(yōu)目標(biāo)函數(shù)值
 
 
 
#==打印結(jié)果===
min_index=np.argmin(Tau)#最優(yōu)值索引
minX=X[min_index,0]  #最優(yōu)變量x
minY=X[min_index,1]  #最優(yōu)變量y
minValue=func(X[min_index,0],X[min_index,1])  #最優(yōu)目標(biāo)函數(shù)值
 
print('最優(yōu)變量x',minX,end='')
print('最優(yōu)變量y',minY,end='\n')
print('最優(yōu)目標(biāo)函數(shù)值',minValue)
 
plt.plot(fitneess_value_list,label='迭代曲線')
plt.legend()
plt.show()

6.3 結(jié)果

最優(yōu)變量x 5.0最優(yōu)變量y 5.0
最優(yōu)目標(biāo)函數(shù)值 -123.7

6.4 案例2

                        

6.5 Python實(shí)現(xiàn) 

#====================導(dǎo)入相關(guān)庫(kù)=============================
import pandas as pd
import numpy as np
from tqdm import tqdm#進(jìn)度條設(shè)置
import matplotlib.pyplot as plt
import matplotlib; matplotlib.use('TkAgg')
from pylab import *
mpl.rcParams['font.sans-serif'] = ['SimHei']
mpl.rcParams['axes.unicode_minus'] = False
 
 
#=======================定義函數(shù)==========================
 
#=======目標(biāo)函數(shù)=====
def calc_f(X):
    """計(jì)算粒子的的適應(yīng)度值,也就是目標(biāo)函數(shù)值,X 的維度是 size * 2 """
    A = 10
    pi = np.pi
    x = X[0]
    y = X[1]
    return 2 * A + x ** 2 - A * np.cos(2 * pi * x) + y ** 2 - A * np.cos(2 * pi * y)
 
#====懲罰項(xiàng)函數(shù)======
def calc_e(X):
    """計(jì)算螞蟻的懲罰項(xiàng),X 的維度是 size * 2 """
    ee = 0
    """計(jì)算第一個(gè)約束的懲罰項(xiàng)"""
    e1 = X[0] + X[1] - 6
    ee += max(0, e1)
    """計(jì)算第二個(gè)約束的懲罰項(xiàng)"""
    e2 = 3 * X[0] - 2 * X[1] - 5
    ee += max(0, e2)
    return ee
 
#===子代和父輩之間的選擇操作====
def update_best(parent,parent_fitness,parent_e,child,child_fitness,child_e):
    """
        針對(duì)不同問(wèn)題,合理選擇懲罰項(xiàng)的閾值。本例中閾值為0.00001
        :param parent: 父輩個(gè)體
        :param parent_fitness:父輩適應(yīng)度值
        :param parent_e    :父輩懲罰項(xiàng)
        :param child:  子代個(gè)體
        :param child_fitness 子代適應(yīng)度值
        :param child_e  :子代懲罰項(xiàng)
        :return: 父輩 和子代中較優(yōu)者、適應(yīng)度、懲罰項(xiàng)
        """
    # 規(guī)則1,如果 parent 和 child 都沒(méi)有違反約束,則取適應(yīng)度小的
    if parent_e <= 0.00001 and child_e <= 0.00001:
        if parent_fitness <= child_fitness:
            return parent,parent_fitness,parent_e
        else:
            return child,child_fitness,child_e
    # 規(guī)則2,如果child違反約束而parent沒(méi)有違反約束,則取parent
    if parent_e < 0.00001 and child_e  >= 0.00001:
        return parent,parent_fitness,parent_e
    # 規(guī)則3,如果parent違反約束而child沒(méi)有違反約束,則取child
    if parent_e >= 0.00001 and child_e < 0.00001:
        return child,child_fitness,child_e
    # 規(guī)則4,如果兩個(gè)都違反約束,則取適應(yīng)度值小的
    if parent_fitness <= child_fitness:
        return parent,parent_fitness,parent_e
    else:
        return child,child_fitness,child_e
 
#=======================初始化參數(shù)==========================
m=20                   #螞蟻個(gè)數(shù)
G_max=200              #最大迭代次數(shù)
Rho=0.9                #信息素蒸發(fā)系數(shù)
P0=0.2                 #轉(zhuǎn)移概率常數(shù)
XMAX= 2               #搜索變量x最大值
XMIN= 1              #搜索變量x最小值
YMAX= 0               #搜索變量y最大值
YMIN= -1              #搜索變量y最小值
step=0.1                #局部搜索步長(zhǎng)
P=np.zeros(shape=(G_max,m)) #狀態(tài)轉(zhuǎn)移矩陣
fitneess_value_list=[] #迭代記錄最優(yōu)目標(biāo)函數(shù)值
 
#=======================初始化螞蟻群體位置和信息素==========================
def initialization():
    """
    :return: 初始化蟻群和初始信息素
    """
    X = np.zeros(shape=(m, 2))  # 蟻群 shape=(20, 2)
    Tau = np.zeros(shape=(m,))  # 信息素
    for i in range(m):  # 遍歷每一個(gè)螞蟻
        X[i, 0] = np.random.uniform(XMIN, XMAX, 1)[0]  # 初始化x
        X[i, 1] =np.random.uniform(YMIN, YMAX, 1)[0]  # 初始化y
        Tau[i] = calc_f(X[i])#計(jì)算信息素
    return X,Tau
 
#===位置更新====
def position_update(NC,P,X):
    """
    :param NC: 當(dāng)前迭代次數(shù)
    :param P: 狀態(tài)轉(zhuǎn)移矩陣
    :param X: 蟻群
    :return: 蟻群X
    """
    lamda = 1 / (NC + 1)
    # =======位置更新==========
    for i in range(m):  # 遍歷每一個(gè)螞蟻
        # ===局部搜索===
        if P[NC, i] < P0:
            temp1 = X[i, 0] + (2 * np.random.random() - 1) * step * lamda  # x(2 * np.random.random() - 1) 轉(zhuǎn)換到【-1,1】區(qū)間
            temp2 = X[i, 1] + (2 * np.random.random() - 1) * step * lamda  # y
        # ===全局搜索===
        else:
            temp1 = X[i, 0] + (XMAX - XMIN) * (np.random.random() - 0.5)
            temp2 = X[i, 0] + (YMAX - YMIN) * (np.random.random() - 0.5)
 
        # =====邊界處理=====
        if (temp1 < XMIN) or (temp1 > XMAX):
            temp1 = np.random.uniform(XMIN, XMAX, 1)[0]  # 初始化x
        if (temp2 < YMIN) or (temp2 > YMAX):
            temp2 = np.random.uniform(YMIN, YMAX, 1)[0]  # 初始化y
 
        #=====判斷螞蟻是否移動(dòng)(選更優(yōu))=====
        #==子代螞蟻==
        children=np.array([temp1,temp2])#子代個(gè)體螞蟻
        children_fit=calc_f(children) #子代目標(biāo)函數(shù)值
        children_e=calc_e(children) #子代懲罰項(xiàng)
        parent=X[i]#父輩個(gè)體螞蟻
        parent_fit=calc_f(parent)#父輩目標(biāo)函數(shù)值
        parent_e=calc_e(parent)#父輩懲罰項(xiàng)
 
        pbesti, pbest_fitness, pbest_e = update_best(parent, parent_fit, parent_e, children, children_fit,children_e)
        X[i]=pbesti
    return X
 
#======信息素更新============
def Update_information(Tau,X):
    """
    :param Tau: 信息素
    :param X: 螞蟻群
    :return: Tau信息素
    """
    for i in range(m):  # 遍歷每一個(gè)螞蟻
        Tau[i] = (1 - Rho) * Tau[i] + calc_f(X[i]) #(1 - Rho) * Tau[i] 信息蒸發(fā)后保留的
    return Tau
 
#=============主函數(shù)======================
def main():
    X,Tau=initialization() #初始化螞蟻群X 和信息素 Tau
    for NC in tqdm(range(G_max)):  # 遍歷每一代
        BestIndex = np.argmin(Tau)  # 最優(yōu)索引
        Tau_best = Tau[BestIndex]  # 最優(yōu)信息素
        # 計(jì)算狀態(tài)轉(zhuǎn)移概率
        for i in range(m):  # 遍歷每一個(gè)螞蟻
            P[NC, i] = np.abs((Tau_best - Tau[i])) / np.abs(Tau_best) + 0.01  # 即離最優(yōu)信息素的距離
        # =======位置更新==========
        X=position_update(NC,P,X) #X.shape=(20, 2)
 
        # =====更新信息素========
        Tau=Update_information(Tau, X)
 
        # =====記錄最優(yōu)目標(biāo)函數(shù)值========
        index = np.argmin(Tau)  # 最小值索引
        value = Tau[index]  # 最小值
        fitneess_value_list.append(calc_f(X[index]))  # 記錄最優(yōu)目標(biāo)函數(shù)值
 
    #=====打印結(jié)果=======
    min_index = np.argmin(Tau)  # 最優(yōu)值索引
    minX = X[min_index, 0]  # 最優(yōu)變量x
    minY = X[min_index, 1]  # 最優(yōu)變量y
    minValue = calc_f(X[min_index])  # 最優(yōu)目標(biāo)函數(shù)值
 
    print('最優(yōu)變量x', minX, end='') 
    print('最優(yōu)變量y', minY, end='\n')
    print('最優(yōu)目標(biāo)函數(shù)值', minValue)
    print('最優(yōu)變量對(duì)應(yīng)的懲罰項(xiàng)',calc_e(X[min_index]))
    #=====可視化=======
    plt.plot(fitneess_value_list, label='迭代曲線')
    plt.legend()
    plt.show()
 
 
 
if __name__=='__main__':
    main()
 
 

6.6 結(jié)果

100%|██████████| 200/200 [00:00<00:00, 220.49it/s]
最優(yōu)變量x 1.0000085699291246最優(yōu)變量y -0.0040192755525732165
最優(yōu)目標(biāo)函數(shù)值 1.0032219250172503
最優(yōu)變量對(duì)應(yīng)的懲罰項(xiàng) 0

到此這篇關(guān)于Python實(shí)現(xiàn)蟻群算法的文章就介紹到這了,更多相關(guān)Python 蟻群算法內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

最新評(píng)論