itthon » Gomba feldolgozás » A genetikai algoritmusok megoldásokat keresnek. Genetikai algoritmusok alkalmazása

A genetikai algoritmusok megoldásokat keresnek. Genetikai algoritmusok alkalmazása

Nemes ürességről árulkodott. azonban elégtelen szint*a cenzúra által kivágott* kitolta a megjelenés dátumát, és csak most, részemről szégyenletes, unalmas könyörgés után kapott lehetőséget ez a cikk, hogy megmutassa magát a világnak. Ez alatt az idő alatt legalább három (ennyire akadt meg a szemem) cikk hasonló téma, és valószínűleg nem ez az első alkalom, hogy az alábbiakban leírtak egy részét olvassa el. Azt javaslom az ilyen embereknek, hogy ne ráncolják a szemöldöküket egy tapasztalatlan fiatal újabb próbálkozása előtt, hogy a GA-t népszerűsítő tudományos módon magyarázzák el, hanem térjenek át a következő kiállításra, a második részre, amely egy GA-alapú bot létrehozását írja le. a Robocode programozó játék. Ezzel a legfrissebb titkosszolgálati információk szerint még nem találkoztak a hubon.

Első rész. Egy genetikai algoritmus élete és munkája.

Kezdjük messziről. Van egy bizonyos problémakör, amelyet meg kell oldani. Célunk, hogy olyan cselekedeteket találjunk, amelyek képesek átalakulni Adott(a problémák kezdeti feltételei) in Válasz(célállapot).

Ha a helyzet egyszerű, és egy ilyen probléma megoldása egyértelműen kiszámítható a feltételekből ezeknek a matánoknak a segítségével, akkor nagyszerű, itt minden rendben van a bölcsességünk nélkül is, meg vagyunk szarva, mindannyian külön járunk módokon. Például megoldáskor másodfokú egyenlet a választ (x1, x2 értékek) a kezdeti feltételből (a, b, c együtthatók) kapjuk meg az iskolában tanult képlet alkalmazásával. Mit kell tenni szomorúbb esetben, mikor a szükséges képletet nincs benne a tankönyvben? Kipróbálhatod vele ötletelés megoldja az egyik problémát. Analitikusan. Numerikus módszerek. A funkciók kétségbeesett keresésének erejével. Egy idő után megszólal az álmodozó diák, „ha megoldódik magától”. Igen, itt jövünk ki a függöny mögül. Tehát a cél egy olyan program megírása, amely talál egy függvényt (programot), amely bemeneti adatokat fogad és érvényes számokat ad vissza. A metaprogramozás ereje, harcba!

Hmm, hogyan fogjuk elérni ezt a célt? A tűz mellett hozzunk áldozatot a rekurzió isteneinek: írunk egy programot, ami megír egy függvényt (programot)... Nem, ez másodszorra nem megy. Jobb, ha a természetből veszünk példát, és olyan jelenségekre vetjük tekintetünket, mint az evolúció mechanizmusa, természetes kiválasztódás. Minden olyan, mint az életben: a programjaink az alkalmazkodóbb egyedek igája alatt élnek, párosodnak, szülnek és meghalnak, továbbadva őket. legjobb tulajdonságait leszármazottak. Őrülten hangzik, de érdemes közelebbről is megnézni.

Szoftvervilágunk Istene a mi feladatunk. A programoknak hinniük kell benne, párodni kell érte, gyertyát gyújtani érte a templomban, és együtt kell élni vele egyetlen célja- megtalálni az élet értelmét és megoldani ezt a problémát. Aki a legjobban alkalmazkodik a környezethez (közelebb van a probléma megoldásához), az alfahímmé válik, túléli és erős utódokat hoz. Egy vesztes, aki egész életét börtönben töltötte online játékok nem tapasztalt sikert a probléma megoldásában, nagyon kicsi az esélye, hogy utódokat szüljön. A génállomány megtisztul e pattanásos elvtársak hozzájárulásától, és az egész műsortársadalom megmozdul a megoldott probléma fényes jövője felé. Hát be általános vázlat Már világos, most meg kell értened az árnyalatokat: először is, hogyan képzeled el a programok párosítását? másodszor, honnan szerezzük be a programok első generációját? harmadszor, milyen jellemző alapján határozzuk meg az egyedek alkalmasságát, és hogyan befolyásolja a keresztezést? negyedszer, érdemes eldönteni, hogy milyen feltételekkel zárul az algoritmus, és mikor kell leállítani ezt az egész orgiát.

A programpárosítás művészete

Azt hiszem, sokan közülünk néha égető vágyat érez a jelentkezés iránt erőszakos cselekvés szexuális jellegű. Itt kénytelenek vagyunk előre figyelmeztetni, hogy nem ösztönözzük az ilyen fajok közötti eltéréseket. Minden úgy van, ahogy szerettük volna katolikus templom: program programmal, csak házasság után... és nem cserélnek partnert, még akkor sem, ha az a bágyadt srác vett neked egy koktélt a bárban. Bár nem, hazudok, a hárem típusú többnejűség virágzik. Igen, és annak ellenére, hogy az alábbiakban olyan szavakat használunk, mint „apa” vagy „fia”, a programjaink hermafroditák. Nos, vérfertőzés is... Jaj, és beszéltem az egyházról is *facepalm*. Oké, erről majd később.

A programok keresztezésének kérdése nem ilyen egyszerű. A függvények, karakterláncok vagy változók véletlen cseréje kövér szálat eredményez ijesztő szavak neked címezte a fordító/tolmács, és nem új program. Azaz meg kell találni a módot a programok keresztezésére helyesen. Az okos srácok megtalálták a kiutat. És az okos fiúk és lányok, akik a fordítók szerkezetét tanulmányozták, szintén sejtették. Igen, igen, ez egy szintaktikai fa.

Hadd fékezzem meg azonnal a lelkesedésemet: még nem túl vastag a szakállunk, így a legtöbbet fogjuk használni egyszerű típusok programokat. Aki szeretne, bemehet a programozás számtalan gazdagságának völgyébe, de itt minden egyszerű - a program kifejezésekből áll, viszont egyszerű függvényekből áll némi aritással, változókkal és konstansokkal. Minden kifejezés egyet számol a program által visszaadott értékek közül.

Például: néhány egyedi programnégyzet két kifejezésből áll, és megpróbál (nem túl sikeresen) megoldani egy másodfokú egyenletet:
függvény négyzet(a, b, c)(x1 = min(sin(b)*(a+1), 0); x2 = 3 + exp(log(b*a)); return (x1, x2); )
A bemutató mellett döntöttünk, most a tárhelyet kell rendezni. Mivel még mindig nagyon sok tánc van e programok körül, beleértve a rendszer egyik részéből a másikba való áthelyezésüket (amelyek általában az én esetemben általában különböző nyelvek), akkor a mintánkat fa formában tárolni nem túl kényelmes. Többet képviselni kényelmes módon(ideális esetben valamilyen véges ábécé feletti karakterláncok halmaza) az egyéni program-fák_készletének meg kell tanulnia kódolni/dekódolni.

Úgy néz ki, mint egy fa, de nem az
Tehát a fát karakterláncként kell ábrázolnunk. Itt a karvafák ereje lesz segítségünkre. Először is el kell döntenie, hogy milyen függvények, változók és állandók jelenhetnek meg a fában. A változók és konstansok a fa leveleinek felelnek meg, és termináloknak, a függvényeket - a fa fennmaradó (belső) csomópontjainak nevezik - nem termináloknak. Arra is érdemes figyelni, hogy a funkcióknak lehetnek különböző mennyiségbenérvek, ezért valóban szükségünk lesz ilyen tudásra („arity”, a szó csendesen átfutott a szakértők ajkán). Az eredmény egy kódolási tábla, például így:

Itt n, +, *, if függvények; 2 - állandó; a és b változók. BAN BEN valódi problémákat súlytáblázat, ilyen halmazzal nem lehet másodfokú egyenletet megoldani. Szem előtt kell tartania azt a tényt is, hogy a nullával való osztás és más apokalipszis forgatókönyvek elkerülése érdekében minden függvényt a valós számok teljes halmazán kell definiálni (jól, vagy a feladatban használt bármely halmazon). Ellenkező esetben őrködni kell, nulláról logaritmusokat fogni, majd kitalálni, hogy mit csináljunk vele. Nem vagyunk büszke emberek, a könnyebb utat választjuk, kizárva az ilyen lehetőségeket.

Tehát egy ilyen tábla segítségével nem okoz gondot a függvények fától sorra és visszafuttatása. Például a következő sort kaptuk a dekódoláshoz:

A táblázat segítségével azonosítjuk az egyes elemeket, és emlékezünk az aritásra is:

Most az arity segítségével hivatkozásokat helyezünk el a függvény argumentumaira:

Felhívjuk figyelmét, hogy a lista utolsó 3 eleme senkinek nem volt haszna, és értékeik semmilyen módon nem befolyásolják a függvény eredményét. Ez annak köszönhető, hogy az érintett listaelemek száma, a fa csomópontjainak száma állandóan lebeg az aritásuk függvényében. Tehát jobb tartalékokat felhalmozni, mint később egy nem megfelelő fával szenvedni.

Ha most az első elemnél fogva felhúzzuk, akkor a kifejezésfa a kezünkben lóg:

A függvény értéke a fán való rekurzív bejárással számítható ki:

Apám szeme ilyen
Térjünk vissza a legforróbb dologhoz - az átkeléshez. A keresztező programok műveleteit tesszük következő feltételekkel: először is, két párosodó egyed két utódot hoz (azaz a populáció mérete állandó); másodszor, a keresztezés eredményeként a leszármazottaknak bizonyos mértékig rendelkezniük kell mindkét szülő tulajdonságaival (azaz az alma ne guruljon túl messze az almafától). Megtudtuk, hogy a program hogyan lesz ábrázolva - karakterláncok vagy fák halmazaként. Ennek megfelelően madzagként vagy faként keresztezhetők.

A fa keresztezése véletlenszerűen kiválasztott ágak cseréje. A keresztező karakterláncokat többféleképpen is meg lehet valósítani: egypontos rekombináció (darabonkénti ragasztás), kétpontos rekombináció, elemenkénti csere, stb. Hosszú összetett mondatokkal írhatók le részvételi kifejezések, de elég egy pillantás a diagramra, hogy megértsük, mi az:

Csak annyit kell megjegyezni, hogy a rekombinációban a ragasztási helyek véletlenszerűen kerülnek kiválasztásra, csakúgy, mint az elemenkénti keresztezésnél, a csere bizonyos valószínűséggel megtörténik. A fákkal való keresztezés az öröklődés szempontjából ígéretesebbnek tűnik, de nehezebb megvalósítani.

Hé, ez a lány velem van!

A folyamat legintimebb részével foglalkoztunk (sokan már ebben a cikkben is érezték, milyen csekély magánélet szerző). Most térjünk át az egyedpár közötti kapcsolatról a társadalmi alapítványok.

Az egyének generációkra oszlanak. Az új generáció az előző generáció egyedeinek gyermekeiből áll. Kiderült, hogy létezik a fiúk és lányok jelenlegi generációja, az apák és anyák generációja, a nagyszülők, a dédmamák, és így tovább a nulladik generációig - mindennek az ősei büszke emberek. A születés után egy új nemzedék minden egyede megpróbál megoldani egy problémát, cselekedeteit valamilyen isteni erőnléti függvény értékeli, és az ifjúság aktivitásának megítélésétől függően az egyén kap némi esélyt az utódnemzedésre, vagyis az osztályba kerülésre. a nemzésre kiválasztott generáció legjobb képviselői közül. Világunk kemény és kegyetlen, és a disztópiák minden kánonja szerint (vagy a Führer elképzelései szerint, ahogy akarod) a haszontalan nyugdíjas szülők, miután teljesítették küldetésüket, hogy utódokat szüljenek, kirándulnak gázszállító furgon, életteret szabadítva fel pár gyerekük számára. A gyerekek szüleik nyomdokaiba lépnek, és így tovább nemzedékről nemzedékre.

Ugyanazon fitneszfunkciónak (vagy fitneszfunkciónak), amely a párzási kvótákat adja ki, megfelelően fel kell mérnie az egyén képességét a probléma és probléma megoldására. numerikus kifejezés ez az alkalmasság (minél magasabb az érték, annál jobb az alkalmasság). Például ugyanazon másodfokú egyenlet esetében ez annak a mértéke lehet, hogy az egyenlet bal oldalának értéke mennyire közelít a nullához, ha x1, x2 értékeket helyettesítünk, az egyedi program által kiszámítva.

A fitnesz funkció a generáció minden egyedének megad egy bizonyos számot, amely jelzi a hasznosságát és alkalmasságát. Ez az érték befolyásolja a kiválasztási eljárást: minél magasabb egy egyén értéke, annál valószínűbb, hogy talál párat a keresztezéshez (és akár egynél többet is). A gyakorlatban egy generáció összes egyedére vonatkozó alkalmasság kiszámítása után ezeket az értékeket normalizáljuk (úgy, hogy az egyedek fittségének összege 1 legyen), és minden csókolóhelyre sorsot vetünk ( véletlen szám 0-tól 1-ig), meghatározva a szerencsés személyt. Az alfahím szerezhet magának néhány helyet, a vesztes nem kap semmit, és egyedül marad egy kopott 1994-es naptárral Pamellával. Ezt a kiválasztási módszert „rulettválasztásnak” nevezik, és sematikusan így néz ki:

Vannak más kiválasztási módszerek is, de mindegyik betartja Általános szabály: Minél nagyobb az egyén edzettsége, annál inkább részt kell vennie a keresztezésben. Az elitizmus opciót is bevonhatja a folyamatba, amikor legjobb képviselője generációs díjat kap a Hazáért végzett szolgálatokért további évekélet: változtatás nélkül száll át a következő nemzedékre, bár egyidejűleg gyermeket is szülhet. Ez lehetővé teszi, hogy ne veszítsünk sokat jó döntés, amely az átkelés során megsemmisülhet.

Itt említsük meg a mutációt is. Ez egy művelet véletlenszerűen kis valószínűséggel megváltoztatja az egyed egy töredékét, ami lehetővé teszi a génállomány diverzifikálását. Hasznos dolog, hirtelen egy ilyen mutáció segít lebontani a laktózt! És ha nem, és van még egy kéz, akkor a hátralévő napjaiban szenvednie kell vele, még mindig kevés az esélye, hogy utódokat szüljön.

Teremtés és Apokalipszis

Kitaláltuk, hogyan költözzünk nemzedékről nemzedékre, most a kérdés: „mi volt a kiváltó ok, hol kezdődött az egész?” Ellentétben ezzel a világgal, az ilyen dolgok megmagyarázásához nem kell olyan trükköket kitalálnunk, mint " nagy durranás" vagy "7 nap". Itt a válasz nagyon egyértelmű - minden a nulla generációval kezdődött, amelyet véletlenszerűen hoztak létre. Igen, igen, csak véletlenszerűen generálunk sorokat/fákat. Az egyetlen követelmény az egyén helyessége, és senkit sem érdekel, hogy a szelekció mennyire hibás.

Világunk addig létezik, amíg szükségünk van rá. Vagy beállítjuk a minket kielégítő edzettségi szintet, és amikor egy kellően menő egyed megjelenik, leállítjuk a folyamatot, vagy megnézzük, hogy a generáció egyedei mennyiben térnek el egymástól. Logikus, hogy ha az egész nemzedék egypetéjű ikrekből áll, akkor a további párosítás nem ad semmi újat a génállománynak, és naivitás egyetlen mutációban reménykedni. Időkorlátot is beállíthat.

Hé, te! Jó szárnyalni az agyad! Mi a végeredmény?

Tartsunk egy kis szünetet ettől a lenyűgöző igézettől, és nézzünk vissza (hát, felfelé). Összefoglalva, a genetikai algoritmus így néz ki:

Megtanuljuk egy probléma megoldását egyéni genetikai algoritmus formájában ábrázolni - egy rögzített hosszúságú lista valamilyen ábécé alapján. Ezt követően kiválasztunk egy fitneszfüggvényt, amely képes kiértékelni az egyéneket, és véletlenszerűen nulla generációt generál. Itt kezdődik a szabad szerelem körforgása: kiszámítják egy nemzedék egyedeinek alkalmasságát, ezek alapján párok alakulnak ki (a veszteseket kidobják, és az alfahímek nem korlátozódnak egy párra), a megmaradtak párosodnak, szülnek. pár gyerek (akikhez mutáció is kapcsolódik) és öngyilkos lesz. Ez így megy egészen addig, amíg meg nem találjuk a kiválasztottat, vagy a változások már nem tetszenek nekünk, vagy belefáradunk az egészbe. Nos, hogyan bírom diagram nélkül:

Második rész. A genetikai algoritmus szerepe a Robocode bot képében.

Valahogy elhúzódott az első rész, mindannyian elfáradtunk, úgyhogy nem ismételjük meg. Néhány megvalósítási funkciót is kihagyunk.
Itt megtudhatja, mi a Robocode: habrahabr.ru/blogs/programmers_games/59784 (a képek azonban elvesztek). Röviden, ez egy programozási játék, amelyet eredetileg a Java nyelv jellemzőinek tanulmányozására hoztak létre, és amely lehetővé teszi a résztvevők számára, hogy saját robotbotokat hozzanak létre, és csatákat rendezzenek közöttük. Minden résztvevő Java nyelven ír kódot, amely egy kis tankot irányít, és más hasonló tankokkal harcol.

A következő feladat előtt állunk: fejlesztés genetikai algoritmus segítségével automatizált rendszerek tankbot irányítása. A robotot automatikusan kell létrehozni és módosítani, pl. fejlődése során 1 az 1 ellen csatákban „alkalmazkodni” egy adott és előre kiválasztott ellenfélhez.

Hogyan ábrázoljuk a probléma megoldását egyénként

Először is határozzuk meg a tartály képességeit. A robot által a csata során végrehajtható alapvető műveletek listája négy pontra korlátozódik: forgasd el a fegyvert, fordítsd el a testet, lőj, mozogj. Az ötödik akciót, a radarforgatást kizártuk a mérlegelésből, triviálisan végrehajtva - állandó forgásban (így a harckocsi mindig naprakész információval rendelkezik az ellenség helyzetéről).

Nyilvánvaló, hogy a sikeres harchoz ezeket a műveleteket nem kaotikusan kell végrehajtani, hanem a csatatéren uralkodó helyzettől (állapottól): a tankok helyzetétől, sebességétől, energiájától és egyéb paramétereitől függenek. Így a tank irányításának folyamata a fenti műveletek végrehajtásához vezet a csata állapota alapján. Azt a törvényt, amely a harctéri helyzet alapján meghatározza a harckocsi viselkedését (cselekvését), irányító funkciónak nevezzük, és ez lesz a genetikai algoritmusunk egyede.

Mivel a vezérlő funkciónak 4 értéket kell visszaadnia (lövési energiát, torony elfordulási szögét, hajótest elfordulási szögét, tank mozgását), így az utolsó részben leírtak szerint négy kifejezésből fog állni, pl. négy sorból/fából.

A kódolási táblázat összeállításához el kell döntenie az alapvető függvények, változók és állandók halmazáról.

Funkciók:
+(x, y) = x + y
++(x, y, z) = x + y + z
n(x) = -x
*(x, y) = x * y
**(x, y) = x * y * z
min(x, y) = x > y? y:x
s(x) = 1/(1+exp(-x))
if(x, y, z, w) = x > y? z:w

Változók:
x, y - az ellenfél tankjának koordinátái a tankunkhoz képest;
dr az a távolság, amely még hátra van, amíg a tankunk „eléri”;
tr az a szög, amelyben a tartályunk még elfordul;
w a tartályunk és a mező széle közötti távolság;
dh az ellenséges harckocsi iránya és a tankunk lövege közötti szög;
GH a harckocsink fegyverének forgásszöge;
h - az ellenfél tankjának mozgási iránya;
d a tankunk és az ellenfél tankja közötti távolság;
e az ellenfél tankjának energiája;
E a tartályunk energiája.

Nos, konstansok: 0,5, 0, 1, 2, 10

Fitness funkció

Írjuk le, hogyan választották a fitnesz funkciót. A Robocode számos árnyalat alapján generálja a csata eredményét. Ez nem csak a győzelmek száma, hanem mindenféle pont az aktivitásért, a túlélésért, az ellenfél eltalálásáért stb. Ennek eredményeként a „Robocode” a robotokat az „összes pontszám” paraméter szerint rangsorolja, amely figyelembe veszi a fent leírt összes finomságot. Ezt használjuk az egyed edzettségének számításakor: a végső edzettség egyenlő lesz a tankunk pontjainak százalékos arányával mindkét tank pontjainak összegéből, és 0 és 100 közötti értéket vesz fel. Ennek megfelelően, ha az edzettségi érték több mint 50, akkor a robotunk több pontot szerzett, mint az ellenfél, ezért erősebb nála. Vegye figyelembe, hogy ennek a pontozási rendszernek megfelelően az első helyet nem mindig az foglalja el, aki a csata fordulóinak többségét megnyerte. Nos, itt megvonjuk a vállunkat a robogóra vonatkozó mondattal: az alkotók meghatározták a kritériumokat, mi betartjuk azokat.

Általánosságban elmondható, hogy az egyén alkalmasságának kiszámítása egy harcsorozat lebonyolítását jelenti! Azok. Egy ilyen jelentéktelennek tűnő pont, mint a fitnesz téves számítása, az ilyen tamburával való táncokból áll:
1) Rendszerünk elmenti az egyed kódolt kromoszómáit a chromosome.dat fájlba;
2) Mindenki számára elindul a „Robocode” környezet, amely párbajt szervez. Egy .battle formátumú fájllal látjuk el, amely leírja a csata körülményeit - a harckocsik listája, a mező mérete, a körök száma stb.;
3) A harchoz a Robocode tankokat tölt be, a shell robotunk beolvassa a chromosome.dat fájlt kódolt viselkedéssel, akciók sorozatává értelmezi és ezek szerint vezeti le a csatát;
4) A küzdelem végén a Robocode környezet beírja a csata eredményét a results.txt fájlba, és befejezi a munkáját;
5) Rendszerünk kiválasztja ezt a fájlt, elemzi, és kivonja belőle a tankunk és az ellenfél összpontszámát. Egyszerű aritmetikával megkapjuk az alkalmassági értéket.

Mint a miénk, igaz?

Foglaljuk össze a mi tervezőiroda. Rendszerünk két részből (programokból) áll. Közülük az első egy genetikai algoritmus alapján összegyűjti az egyedet és elmenti karakterláncok halmazaként, a második (robot kód) pedig értelmezi (kifejezésfává dolgozza fel) és vezérli a tankot (az érték kiszámításával). kifejezésfák adott változókkal rekurzív bejárással, azaz jelen állapot csata). Az első program SI nyelven, a második Java nyelven készült.

A genetikai algoritmus megvalósítása során a populáció egyedszámát 51-re (25 pár + egy elit egyed) választottuk. Az evolúció egy lépése (népességváltozás) körülbelül egy tucat percet vesz igénybe, így összességében több órán keresztül elhúzódik az ügy.

Ennek eredményeként bemutatjuk a Walls és a Crazy robotok riválisának létrehozásának eredményeit:




Az első esetben leállítottuk a folyamatot, miután az egyik egyed elérte a 70-es edzettségi szintet, nekünk elég volt, ha az egyedek átlagos edzettsége egy generációban meghaladta az 50-et.

Szemlélődés után öblítse ki a szemét alkohollal

Ha valaki nem fél vérkönnyeket sírni görcsökben a redneck kódolás elmélkedésétől (főleg a robotkódtól kezd mozdulni a haj - kölcsönös gyűlölködésünk van a java-val), akkor csatolom

Az egyik feladat intelligens rendszerek az optimális megoldás keresése: amikor a rendszert számos külső és belső tényezők, az intelligens eszköznek mindet figyelembe kell vennie, és az előnye szempontjából optimális viselkedést kell választania. Tegyük fel, hogy ha Ön egy raktár tulajdonosa, számos tényezőt kell figyelembe vennie (áruegységek költsége, kereslet, különféle áruk raktárban való tárolásának költségei stb.), hogy minimalizálja a költségeket és a legnagyobb profitot érje el.

Egy másik példa: csúszós úton haladsz, és az autója hirtelen csúszásba kezd, néhány méterrel tőle jobb oldalon van egy oszlop, és egy teherautó halad a szembejövő sávban. Figyelem a kérdésre: hogyan lehet kikerülni a helyzetből a legkevesebb veszteséggel, vagy ami még jobb, ezek nélkül. Sok tényezőt kell figyelembe venni: a sebességed és a szembejövő autó sebessége, az oszloptól való távolság, a csúszás „meredeksége” stb. Mit kell csinálnunk? Adja meg a gázt, próbáljon kijutni a csúszásból, vagy fékezzen, esetleg próbáljon meg óvatosan az árokba csúszni, hogy ne ütközzen oszlopnak. Számos lehetőség létezik, és az optimális kiválasztásához mindegyiket ki kell próbálnia. Legyen számítógépes játék- menthetsz és játszhatsz addig, amíg az eredmény meg nem felel. Ez az optimális megoldás keresése.

A rendszerekben mesterséges intelligencia ilyen problémák megoldására használják.

Genetikai algoritmusok– adaptív keresési módszerek, amelyeket funkcionális optimalizálási problémák megoldására használnak. Az evolúció mechanizmusain és modelljein, valamint biológiai algoritmusok genetikai folyamatain alapulnak.

Leegyszerűsítve: lényegében a genetikai algoritmus egy olyan módszer, amely megoldásokat számlál olyan problémákra, amelyekre nem lehet megoldást találni. matematikai képletek. Egy összetett többdimenziós probléma megoldásainak egyszerű felsorolása azonban végtelenül hosszú időt vesz igénybe. Ezért a genetikai algoritmus nem minden megoldást keres, hanem csak a legjobbakat. Az algoritmus felvesz egy csoport megoldást, és megkeresi közöttük a legmegfelelőbbet. Aztán kicsit megváltoztatja őket - új megoldásokat kap, amelyek közül ismét kiválasztja a legjobbat, és elveti a legrosszabbat. Így az algoritmus a munka minden lépésében kiválasztja a legmegfelelőbb megoldásokat (kiválasztást végez), hisz azok a következő lépésben még több eredményt adnak. legjobb megoldások(fejlődik).

Mi köze a biológiának ehhez?

Amint már érted, a genetikai algoritmusok elméletében analógia van a feladat és a feladat között biológiai folyamat. Innen a terminológia...

Egyedi– egy megoldás a problémára.

Népesség— egy probléma megoldásának összessége. Az algoritmus elején véletlenszerűen generálunk egy megoldáshalmazt (kezdeti sokaságot). Ezek a megoldások egyre jobbak lesznek (fejlődnek), ahogy az algoritmus addig működik, amíg eleget nem tesznek a probléma feltételeinek.

És azonnal a legegyszerűbb klasszikus példa. Tegyük fel, hogy a robotnak hat ellenőrzőpontot kell megkerülnie legkevesebb időt. Az egyes pontok közötti távolság távolságmátrixként van megadva.

Ez az utazó értékesítő (utazó) probléma egy változata - az NP-teljes osztályba tartozik, vagyis nem oldható meg matematikai képletekkel.

A probléma megoldása a vezérlőpontok átadásának sorozata. Vegyünk néhányat lehetséges megoldások(magánszemélyek) – ez az.

A döntési minőség definíciói

Fitness funkció– egy populáció egyedeinek minőségét meghatározó funkció. Példánkban ez lesz a kiválasztott útvonalon a pontok közötti távolságok összege.

FP = P(1)+P(2)+P(3)+P(4)+P(5)+P(6),

ahol P(1) ... P(6) a távolság mátrixból való megfelelő átmenet pontjai közötti távolság

Meg kell tehát találnunk a minimális távolságot, mint kisebb érték FP az egyén számára, annál jobb.

Számítsuk ki a fitnesz függvényeket. Az első személynek:

A fennmaradó egyedeknél ugyanígy kapunk.

Körülbelül négy éve, az egyetemen hallottam egy optimalizálási módszerről, amit genetikai algoritmusnak neveznek. Pontosan két dolgot jelentettek róla mindenhol: menő és nem dolgozik. Illetve működik, de lassú, megbízhatatlan, és nem szabad sehol használni. De szépen be tudja mutatni az evolúció mechanizmusait. Ebben a cikkben megmutatom gyönyörű módon nézze meg élőben az evolúció folyamatait ennek munkájának példáján egyszerű módszer. Csak egy kis matematikára, programozásra és némi képzelőerőre van szüksége.

Röviden az algoritmusról

Tehát mi az a genetikai algoritmus? Ez mindenekelőtt egy módszer többdimenziós optimalizálás, azaz módszer egy többdimenziós függvény minimumának meghatározására. Potenciálisan ez a módszer használható globális optimalizálásra, de ezzel kapcsolatban vannak nehézségek, amelyeket később ismertetek.

A módszer lényege, hogy moduláljuk az evolúciós folyamatot: van valamiféle populációnk (vektorkészletünk), amely szaporodik, amelyre hatással vannak a mutációk és a természetes szelekció a minimalizálás alapján történik. objektív funkció. Nézzük meg közelebbről ezeket a folyamatokat.

Tehát először is lakosságunknak kell szaporodnak. A szaporodás alapelve, hogy az utód hasonlít a szüleire. Azok. definiálnunk kell valamiféle öröklődési mechanizmust. És jobb lesz, ha benne van a véletlen eleme is. De az ilyen rendszerek fejlődési üteme nagyon alacsony - a genetikai sokféleség csökken, a populáció degenerálódik. Azok. a függvény értéke megszűnik minimalizálni.

A probléma megoldására egy mechanizmust vezettek be mutációk, amely egyes egyedeknél véletlenszerű változásokból áll. Ez a mechanizmus lehetővé teszi, hogy valami újat vigyünk be a genetikai sokféleségbe.
A következő fontos mechanizmus az kiválasztás. Mint elhangzott, a szelekció olyan egyedek kiválasztása (esetleg a most születettek közül, vagy mindegyikből - a gyakorlat azt mutatja, hogy ez nem játszik döntő szerepet), amelyek jobban minimalizálják a funkciót. Általában annyi egyedet választanak ki, ahány a szaporodás előtt volt, így korszakról korszakra állandó mennyiség egyedek egy populációban. Szokásos a „szerencséseket” is kiválasztani - bizonyos számú egyedet, akik esetleg nem minimalizálják jól a funkciót, de sokszínűséget vezetnek be a következő generációkban.

Ez a három mechanizmus legtöbbször nem elegendő a funkció minimalizálásához. Így degenerálódik a népesség - a helyi minimum előbb-utóbb az egész lakosságot elnyomja értékével. Amikor ez megtörténik, az ún felráz(az analógiák természetében - globális katasztrófák), amikor szinte a teljes populáció elpusztul, és új (véletlen) egyedek jönnek létre.

Itt található a klasszikus genetikai algoritmus leírása, könnyen megvalósítható, és van hely a képzeletnek és a kutatásnak.

A probléma megfogalmazása

Szóval, amikor már eldöntöttem, hogy megpróbálom megvalósítani ezt a legendás (bár sikertelen) algoritmust, a beszélgetés arra terelődött, hogy mit minimalizáljak? Általában valami ijesztő többdimenziós függvényt töltenek be szinuszokkal, koszinuszokkal stb. De ez nem túl érdekes és egyáltalán nem egyértelmű. Egy egyszerű ötlet merült fel - egy kép, ahol az érték felelős a fényerőért, tökéletes egy többdimenziós vektor megjelenítésére. Tehát beléphetünk egyszerű funkció- a célképünk távolsága, a pixel fényerő különbségében mérve. Az egyszerűség és a gyorsaság kedvéért 0 vagy 255 fényerővel készítettem képeket.

Matematikai szempontból az ilyen optimalizálás puszta apróság. Egy ilyen függvény grafikonja egy hatalmas többdimenziós „lyuk” (mint az ábrán egy háromdimenziós parabaloid), amelybe óhatatlanul belecsúszik, ha követi a gradienst. Az egyetlen lokális minimum a globális. .

A probléma csak az, hogy már a minimumhoz közelítve jelentősen lecsökken azoknak az utaknak a száma, amelyeken le lehet menni, és összesen annyi irányunk van, ahány dimenzió (azaz a pixelek száma). Nyilvánvalóan nem érdemes genetikai algoritmussal megoldani ezt a problémát, de érdekes folyamatokat tekinthetünk meg populációnkban.

Végrehajtás

Az első bekezdésben leírt valamennyi mechanizmust végrehajtották. A reprodukálást az „anya” és az „apa” véletlenszerű pixeleinek egyszerűen keresztezésével végezték. A mutációkat úgy végezték el, hogy egy véletlenszerű egyedben egy véletlen pixel értékét az ellenkezőjére változtatták. A rázást pedig akkor hajtották végre, ha a minimum öt lépés alatt nem változott. Ezután „szélsőséges mutáció” következik be - a helyettesítés a szokásosnál intenzívebben történik.

A kezdeti képeknek a nonogrammokat („japán szkennelőszavak”) vettem, de őszintén szólva, lehet csak fekete négyzeteket venni - nincs különbség. Az alábbiakban több kép eredményét láthatjuk. Itt a „házon” kívül mindenkinél egyedenként átlagosan 100 volt a mutációk száma, 100 egyed volt a populációban, a szaporodás során a populáció 4-szeresére nőtt. Minden korszakban 30% volt a szerencsés. A házhoz kisebb értékeket választottak (30 egyed a populációban, egyedenként 50 mutáció).




Kísérletileg megállapítottam, hogy a „szerencsések” használata a szelekcióban csökkenti a populáció minimálisra hajlamosságát, de segít kilábalni a stagnálásból – a „szerencsések” nélkül a stagnálás állandó lesz. Ami a grafikonokon látszik: a bal oldali grafikon a „fáraó” populáció alakulását mutatja szerencsésekkel, a jobb oldali szerencsések nélküli.


Így azt látjuk, hogy ez az algoritmus lehetővé teszi a probléma megoldását, bár nagyon hosszú ideje. Túl sok nagyszámú rázkódás, nagy képek esetén megoldható nagy mennyiség egyedek egy populációban. A különböző dimenziókhoz tartozó paraméterek optimális kiválasztását a bejegyzés keretein kívül hagyom.

Globális optimalizálás

Mint említettük, a lokális optimalizálás meglehetősen triviális feladat, még nagy dimenziós esetekben is. Sokkal érdekesebb látni, hogyan birkózik meg az algoritmus a globális optimalizálással. Ehhez azonban először létre kell hoznia egy függvényt sok helyi minimummal. És a mi esetünkben ez nem olyan nehéz. Elegendő a minimumot a távolságokból több képre (ház, dinoszaurusz, hal, csónak) átvenni. Ezután a kezdeti algoritmus „becsúszik” valami véletlenszerű lyukba. És többször is futtathatja.

De van több is érdekes megoldás adott probléma: megérthetjük, hogy egy lokális minimumba csúsztunk, erős felrázást hajtunk végre (vagy akár újra kezdeményezünk egyéneket), majd az ismert minimumhoz közeledve büntetéseket adunk hozzá. Mint látható, a képek váltakoznak. Felhívjuk figyelmét, hogy nincs jogunk hozzányúlni eredeti funkciója. De emlékezhetünk a helyi minimumokra, és magunk is büntethetünk.

Ezen a képen az az eredmény látható, amikor egy lokális minimum (erős stagnálás) elérésekor a populáció egyszerűen kihal.

Itt a populáció kihal, és egy kis büntetést adnak hozzá (ami megegyezik a normál távolsággal egy ismert minimumhoz képest). Ez nagymértékben csökkenti az ismétlések valószínűségét.

Érdekesebb, ha a populáció nem hal ki, hanem egyszerűen elkezd alkalmazkodni az új feltételekhez (következő ábra). Ez 0,000001 * összeg ^ 4 büntetéssel érhető el. Ebben az esetben az új képek kissé zajosak lesznek:

Ezt a zajt a büntetés max(0,000001 * összeg ^ 4, 20) értékre való korlátozásával küszöböljük ki. De látjuk, hogy a negyedik lokális minimumot (dinoszauruszt) nem lehet elérni – valószínűleg azért, mert túl közel van valamelyik másikhoz.

Biológiai értelmezés


Milyen következtetéseket vonhatunk le – merjem ki – a modellezésből? Először is látjuk szexuális szaporodás- a fejlődés és az alkalmazkodóképesség legfontosabb motorja. De ez önmagában nem elég. A véletlenszerű, apró változtatások szerepe rendkívül fontos. Ők biztosítják az evolúció során új állatfajok megjelenését, hazánkban pedig a populáció sokszínűségét.

A Föld evolúciójában a legfontosabb szerepet az játszotta a természeti katasztrófákés tömeges kihalások (dinoszauruszok, rovarok stb. kihalása – körülbelül tíz fő volt – lásd az alábbi ábrát). Ezt szimulációnk is megerősítette. A „szerencsések” kiválasztása pedig ezt mutatta leginkább gyenge organizmusok napjaink a jövőben a következő generációk alapjává válhatnak.

Ahogy mondják, minden olyan, mint az életben. Ez a „csináld magad” evolúciós módszer világosan mutatja érdekes mechanizmusokés szerepük a fejlődésben. Természetesen van még sok érdemesebb evolúciós modell (természetesen a difúrokon alapuló), több, az élethez közelebb álló tényezőt figyelembe véve. Természetesen több is van hatékony módszerek optimalizálás.

P.S.

Matlabban (vagy inkább Octave-ban) írtam egy programot, mert itt minden egy csupasz mátrix, és vannak eszközök a képekkel való munkához. A forráskód mellékelve.

Forrás

függvény res = genetikai(fájl) %generáló globális A B; im2line(fájl); dim = hossz(A(1,:)); szám = 100; reprod = 4; mut = 100; kiválasztás = 0,7; stagnálás = 0,8; pop = round(rand(count,dim)); res = ; B = ; localmin = ; localcount = ; k = 1:300 %reprodukció esetén j = 1:count * reprod pop = ; vége %mutáció idx = 10 * (hossz(res) > 5 && std(res(1:5)) == 0) + 1; for j = 1:count * mut a = floor(rand() * count) + 1; b = padló(rand() * dim) + 1; pop(a,b) = ~pop(a,b); vége %kiválasztás val = func(pop); érték(1:count) = érték(1:count) * 10; npop = nullák(count,dim); = sort(érték); res = ; opt = pop(i(1),:); fn = sprintf("eredmény/%05d-%d.png",k,s(1)); line2im(opt*255,fn); if (s(1) == 0 || localcount > 10) localmin = ; localcount = ; B = ; % pop = round(rand(count,dim)); folytatni;

% szünet;

end for j = 1:floor(count * select) npop(j,:) = pop(i(j),:); end %adad luckers for j = (floor(count*select)+1) : count npop(j,:) = pop(floor(rand() * count) + 1,:); vége %fixing stagnálás if (length(res) > 5 && std(res(1:5)) == 0) if (localmin == res(1)) localcount = localcount+1; egyébként helyi szám = 1; end localmin = res(1); for j = 1:count*stagn a = floor(rand() * count) + 1; npop(a,:) = crossingover(npop(a,:),rand(1,dim)); end end pop = npop; vége res = res(hossz(res):-1:1); vége függvény res = crossingover(a, b) x = round(rand(size(a))); res = a .* x + b .* (~x); vége függvény res = func(v) globális A B; res = inf; ha i = 1:méret(A,1) res = min(res,sum(v ~= A(i,:),2)); vége i = 1 esetén:méret(B,1) res = res + max(0,000001 * sum(v == B(i,:),2) .^ 4,20); end end function = im2line(files) global A sz; A = ; fájlok = cellstr(fájlok); for i = 1:size(files,1) imorig = imread(char(files(i,:))); sz = méret(imorig); A = )]; vége A = A / 255; vége függvény = line2im(im,file) global sz; imwrite(reshape(im*255,sz),file); vége Címkék: Címkék hozzáadása BAN BEN Utóbbi időben Egyre több szó esik újszerű algoritmusokról, mint pl
neurális hálózatok

és genetikai algoritmus. Ma a genetikai algoritmusokról fogok beszélni, de ezúttal próbáljuk meg elkerülni a homályos definíciókat és az összetett kifejezéseket.

Ahogy a Wikipédia mondja: „A genetikai algoritmusok alapító atyja John Holland volt, aki 1975-ben felvetette az ötletet, hogy a genetikát saját céljaira használja fel.” Referenciaként ugyanabban az évben jelent meg az Altair 8800, és nem, nem terrorista, hanem az első személyi számítógép. John ekkor már 46 éves volt.

Hol használják?

Mivel az algoritmus öntanuló, az alkalmazások köre rendkívül széles:
  • Grafikon problémák
  • Elrendezési feladatok
  • Ütemezés
  • A "mesterséges intelligencia" létrehozása

Működési elve

A genetikai algoritmus elsősorban evolúciós algoritmus, más szóval az algoritmus fő jellemzője a keresztezés (kombináció). Ahogy sejthető, az algoritmus ötlete pimaszul a természettől származik, szerencsére nem fog perelni érte. Tehát a felsorolás és, ami a legfontosabb, a kiválasztás révén megkapjuk a helyes „kombinációt”.
Az algoritmus három szakaszra oszlik:
  • Keresztezés
  • Tenyésztés (szelekció)
  • Új generáció kialakulása
Ha az eredmény nem felel meg nekünk, ezeket a lépéseket addig ismételjük, amíg az eredmény el nem kezd eleget tenni, vagy a következő feltételek valamelyike ​​be nem következik:
  • A generációk (ciklusok) száma eléri az előre kiválasztott maximumot
  • A mutáció ideje lejárt
További részletek a lépésekről
Új populáció létrehozása. Ebben a lépésben létrejön egy kezdeti sokaság, amely nagy valószínűséggel nem lesz kóser, de nagy a valószínűsége annak, hogy az algoritmus kijavítja ezt a problémát. A lényeg az, hogy megfeleljenek a „formátumnak”, és „reprodukcióhoz igazodjanak”.
Reprodukció. Nos, itt minden olyan, mint az embereknél, két szülő kell ahhoz, hogy leszármazzon. A lényeg az, hogy a leszármazott (gyermek) örökölje tulajdonságait a szüleitől. Ugyanakkor mindenki reprodukál, nem csak a túlélők (ez a mondat különösen abszurd, de mivel minden gömb vákuumban van, minden lehetséges), másképp kiemelkedik egy alfahím, akinek a génjei átfedik az összes többit, és ez számunkra alapvetően elfogadhatatlan.
Mutációk. A mutációk hasonlóak a szaporodáshoz;
Kiválasztás. Itt kezdődik a legédesebb rész, elkezdjük kiválasztani a lakosságból azoknak a hányadát, akik „tovább mennek”. Ugyanakkor a „túlélők” arányát a kiválasztásunk után előre kézzel határozzuk meg, paraméterként feltüntetve. Sajnos a megmaradt egyéneknek meg kell halniuk.

Gyakorlat

Sikeresen meghallgattad a „tündérmesét” a csodaalgoritmusról, és nagy valószínűséggel vártad, hogy végre elkezdjük használni. Szeretnélek boldoggá tenni, eljött az idő.
Nézzük meg a kedvenc Diofantine-egyenleteim példáját (Equations with integer roots).
Egyenletünk: a+2b+3c+4d=30
Valószínűleg már sejti, hogy a gyökerek adott egyenlet feküdjünk a szegmensre, tehát 5-öt veszünk
véletlenszerű értékek a,b,c,d. (A 30-as határt kifejezetten a feladat egyszerűsítése miatt vettük)
Tehát megvan az első generáció:
  1. (1,28,15,3)
  2. (14,9,2,4)
  3. (13,5,7,3)
  4. (23,8,16,19)
  5. (9,13,5,2)
A túlélési arány kiszámításához minden megoldást behelyettesítünk a kifejezésbe. A kapott érték és a 30 közötti távolság lesz a kívánt értéket.
  1. |114-30|=84
  2. |54-30|=24
  3. |56-30|=26
  4. |163-30|=133
  5. |58-30|=28
Az alacsonyabb értékek közelebb vannak a 30-hoz, ami azt jelenti, hogy kívánatosabbak. Kiderült, hogy nagy értékek alacsonyabb lesz a túlélési arány. A rendszer létrehozásához számoljuk ki az egyes (kromoszómák) kiválasztásának valószínűségét. De a megoldás az, hogy vegyük el az összeget kölcsönös értékek együtthatók, és ez alapján számítsuk ki a százalékokat. ( P.S. 0,135266 - fordított esélyek összege)
  1. (1/84)/0.135266 = 8.80%
  2. (1/24)/0.135266 = 30.8%
  3. (1/26)/0.135266 = 28.4%
  4. (1/133)/0.135266 = 5.56%
  5. (1/28)/0.135266 = 26.4%
Ezután kiválasztunk öt szülőpárt, akiknek pontosan egy gyermekük lesz. Pontosan ötször adunk esélyt, minden alkalommal ugyanannyi lesz a szülővé válás esélye, és egyenlő lesz a túlélés esélyével.
3-1, 5-2, 3-5, 2-5, 5-3
Amint azt korábban említettük, az utód információkat tartalmaz az apa és az anya génjeiről. Ez biztosítható különböző utak, de ebben az esetben"crossover" lesz használva. (| = választóvonal)
  • H.-apa: a1 | b1,c1,d1 H.-anya: a2 | b2,c2,d2 X.-leszármazott: a1,b2,c2,d2 vagy a2,b1,c1,d1
  • H.-apa: a1,b1 | c1, d1 H.-anya: a2,b2 | c2,d2 X.-leszármazott: a1,b1,c2,d2 vagy a2,b2,c1,d1
  • H.-apa: a1,b1,c1 | d1 H.-anya: a2,b2,c2 | d2 X.-leszármazott: a1,b1,c1,d2 vagy a2,b2,c2,d1
Számos módja van az információ átadásának egy leszármazottnak, és a keresztezés csak egy a sok közül. Az elválasztó helye teljesen tetszőleges lehet, valamint az is, hogy az apa vagy az anya a sor bal oldalán lesz-e.
Most tegyük ugyanezt a leszármazottakkal is:
  • H.-apa: (13 | 5,7,3) H.-anya:(1 | 28,15,3) X.-leszármazott: (13,28,15,3)
  • H.-apa: (9,13 | 5,2) H.-anya: (14,9 | 2,4) X.-leszármazott: (9,13,2,4)
  • H.-apa: (13,5,7 | 3) H.-anya: (9,13,5 | 2) X.-leszármazott: (13,5,7,2)
  • H.-apa: (14 | 9,2,4) H.-anya: (9 | 13,5,2) X.-leszármazott: (14,13,5,2)
  • H.-apa: (13,5 | 7, 3) H.-anya: (9,13 | 5, 2) X.-leszármazott: (13,5,5,2)
Most számoljuk ki a leszármazottak túlélési arányát.
  • (13,28,15,3) - |126-30|=96(9,13,2,4) - |57-30|=27
    (13,5,7,2) - |57-30|=22
    (14,13,5,2) - |63-30|=33
    (13,5,5,2) - |46-30|=16

    Szomorú, mert az utódok átlagos edzettsége 38,8-nak bizonyult, a szülőknél ez az együttható 59,4. Ebben a pillanatban célszerűbb egy mutációt használni, egy vagy több értéket 1 és 30 közötti véletlen számmal helyettesítünk.
    Az algoritmus a túlélési arány eléréséig működik egyenlő nullával. Azok. megoldása lesz az egyenletnek.
    Rendszerek nagyobb népesség(például 50 helyett 5, és gyorsabban és stabilabban konvergál a kívánt szintre (0).

    Kód

    Itt ér véget az egyszerűség és kezdődik a csodálatos C++...
    Egy C++ osztályhoz 5 érték szükséges inicializáláskor: 4 együttható és egy eredmény. A fenti példa esetében ez így nézne ki: CDiofantin dp(1,2,3,4,30);

    Ezután az egyenlet megoldásához hívjuk meg a Solve() függvényt, amely visszaadja a megoldást tartalmazó allélt. Hívja a GetGene() parancsot, hogy megkapja a gént a megfelelő a, b, c, d értékekkel. Az ezt az osztályt használó szabványos main.cpp eljárás így nézhet ki:

    #include " " #include "diophantine.h" void main() ( CDiophantine dp(1,2,3,4,30); int ans; ans = dp.Solve(); if (ans == -1) ( cout<< "No solution found." << endl; } else { gene gn = dp.GetGene(ans); cout << "The solution set to a+2b+3c+4d=30 is:\n"; cout << "a = " << gn.alleles << "." << endl; cout << "b = " << gn.alleles << "." << endl; cout << "c = " << gn.alleles << "." << endl; cout << "d = " << gn.alleles << "." << endl; } }

    Maga a CDiofantin osztály:

    #beleértve #beleértve #define MAXPOP 25 struct gén ( int allélok; int fitness; float likelihood; // Egyenlőség vizsgálata. operator==(gén gn) ( for (int i=0;i<4;i++) { if (gn.alleles[i] != alleles[i]) return false; } return true; } }; class CDiophantine { public: CDiophantine(int, int, int, int, int);// Constructor with coefficients for a,b,c,d. int Solve();// Solve the equation. // Returns a given gene. gene GetGene(int i) { return population[i];} protected: int ca,cb,cc,cd;// The coefficients. int result; gene population;// Population. int Fitness(gene &);// Fitness function. void GenerateLikelihoods(); // Generate likelihoods. float MultInv();// Creates the multiplicative inverse. int CreateFitnesses(); void CreateNewPopulation(); int GetIndex(float val); gene Breed(int p1, int p2); }; CDiophantine::CDiophantine(int a, int b, int c, int d, int res) : ca(a), cb(b), cc(c), cd(d), result(res) {} int CDiophantine::Solve() { int fitness = -1; // Generate initial population. srand((unsigned)time(NULL)); for(int i=0;i25) szünet; ) temppop[i] = Fajta(szülő1, szülő2);// Gyermek létrehozása. ) for(i=0;i

    A cikk a Wikipédia és a weboldal anyagain alapul

A genetikai algoritmusok (GA-k) ötlete meglehetősen régen (1950-1975) jelent meg, de igazán csak az utóbbi évtizedekben váltak kutatás tárgyává. Ezen a területen az úttörőnek D. Hollandot tartják, aki sokat kölcsönzött a genetikából, és számítógépekhez adaptálta. A GA-kat széles körben használják mesterséges intelligencia rendszerekben, neurális hálózatokban és optimalizálási problémákban.

Evolúciós keresés

A genetikai algoritmusok modelljei a természet evolúciója és véletlenszerű keresési módszerek alapján készültek. Ebben az esetben a véletlenszerű keresés az evolúció legegyszerűbb funkciójának megvalósítása - a véletlenszerű mutációk és az azt követő szelekció.

Matematikai szempontból az evolúciós keresés nem jelent mást, mint egy létező véges megoldáshalmaz átalakulását újjá. A folyamatért felelős funkció a genetikai keresés. A fő különbség egy ilyen algoritmus és a véletlenszerű keresés között az iterációk (ismétlések) során felhalmozott információk aktív felhasználása.

Miért van szükség genetikai algoritmusokra?

A GA-k a következő célokat követik:

  • az alkalmazkodási mechanizmusok magyarázata mind a természeti környezetben, mind a szellemi kutatási (mesterséges) rendszerben;
  • evolúciós függvények modellezése és alkalmazása különféle, elsősorban optimalizálási problémák hatékony megoldására.

Jelenleg a genetikai algoritmusok és módosított változataik lényege a hatékony megoldások keresése, az eredmény minőségének figyelembevételével. Más szóval, a legjobb egyensúly megtalálása a teljesítmény és a pontosság között. Ez a „legrátermettebb egyén túlélése” jól ismert paradigmája miatt következik be bizonytalan és tisztázatlan körülmények között.

A GA jellemzői

Soroljuk fel a fő különbségeket a GA és a legtöbb egyéb módszer között az optimális megoldás megtalálásához.

  • meghatározott módon kódolt feladatparaméterekkel dolgozik, nem pedig közvetlenül velük;
  • a megoldás keresése nem a kezdeti közelítés finomításával történik, hanem többféle lehetséges megoldásban;
  • csak a célfüggvény használata, annak származékai és módosításai nélkül;
  • valószínűségi megközelítés alkalmazása az elemzésben a szigorúan determinisztikus megközelítés helyett.

Teljesitmény követelmény

A genetikai algoritmusok két feltétel alapján végeznek számításokat:

  1. Adott számú iteráció végrehajtása.
  2. A megtalált megoldás minősége megfelel a követelményeknek.

Ha ezen feltételek valamelyike ​​teljesül, a genetikai algoritmus leállítja a további iterációk végrehajtását. Ezenkívül a megoldási tér különböző régióiból származó GA-k használata lehetővé teszi számukra, hogy sokkal jobban találjanak olyan új megoldásokat, amelyek megfelelőbb célfüggvény-értékekkel rendelkeznek.

Alapvető terminológia

Tekintettel arra, hogy a GA-k genetikán alapulnak, a terminológia nagy része ennek felel meg. Bármely genetikai algoritmus a kezdeti információk alapján működik. A kezdeti értékek halmaza a Pt = (n1, n2, ..., nn) ​​sokaság, ahol pi = (r1, ..., rv). Nézzük meg közelebbről:

  • t az iterációs szám. t1, ..., tk - az algoritmus iterációit jelenti 1-től k-ig, és minden iterációnál új megoldási populáció jön létre.
  • n a populáció mérete Pt.
  • p1, ..., pi - kromoszóma, egyed vagy szervezet. A kromoszóma vagy lánc gének kódolt szekvenciája, amelyek mindegyikének sorszáma van. Nem szabad megfeledkezni arról, hogy a kromoszóma egy egyed (organizmus) speciális esete lehet.
  • A gv olyan gének, amelyek a kódolt oldat részét képezik.
  • A lókusz egy kromoszómán lévő gén sorozatszáma. Az allél egy gén értéke, amely lehet numerikus vagy funkcionális.

Mit jelent a „kódolt” a GA kontextusában? Általában minden érték valamilyen ábécé alapján van kódolva. A legegyszerűbb példa a számok átalakítása decimális számrendszerből bináris ábrázolásra. Így az ábécé halmazként (0, 1) van ábrázolva, és az 15710-es számot az 100111012 kromoszóma fogja kódolni, amely nyolc génből áll.

Szülők és leszármazottak

A szülők olyan elemek, amelyeket egy adott feltételnek megfelelően választanak ki. Például gyakran ilyen feltétel a véletlenszerűség. A kiválasztott elemek a keresztezés és mutáció műveletei révén újakat generálnak, amelyeket leszármazottaknak nevezünk. Így a genetikai algoritmus egy iterációjának végrehajtása során a szülők új generációt hoznak létre.


Végül, az evolúció ebben az összefüggésben generációk váltakozása lesz, amelyek mindegyike más-más kromoszómakészlettel rendelkezik a jobb fittség, vagyis az adott feltételeknek való megfelelőbb megfelelés érdekében. Az evolúció folyamatában az általános genetikai hátteret genotípusnak, az élőlény és a külső környezet közötti kapcsolat kialakulását pedig fenotípusnak nevezzük.

Fitness funkció

A genetikai algoritmus varázsa a fitnesz függvényben rejlik. Minden egyénnek megvan a maga jelentése, amely az adaptációs függvényen keresztül tudható meg. Fő feladata, hogy ezeket az értékeket értékelje a különböző alternatív megoldásokhoz, és válassza ki a legjobbat. Más szóval, a legalkalmasabb.

Az optimalizálási feladatokban a fitneszfüggvényt célfüggvénynek, a vezérléselméletben hibának, a játékelméletben költségfüggvénynek, stb.

Végső soron arra a következtetésre juthatunk, hogy a genetikai algoritmusok egyedek, organizmusok vagy kromoszómák populációját elemzik, amelyek mindegyikét gének kombinációja (néhány érték halmaza) képviseli, és optimális megoldást keresnek a populáció egyedeinek átalakításával. közöttük a mesterséges evolúció.

Az egyes elemek egyik vagy másik irányú eltérései általában összhangban vannak a mennyiségek normális eloszlási törvényével. A GA ugyanakkor biztosítja azon tulajdonságok öröklődését, amelyek közül a leginkább alkalmazkodó fix, ezáltal jobb populációt biztosít.

Alapvető genetikai algoritmus

Bontsuk le lépésről lépésre a legegyszerűbb (klasszikus) GA-t.

  1. A kezdeti értékek inicializálása, vagyis az elsődleges populáció meghatározása, azon egyedek halmaza, amelyekkel az evolúció meg fog történni.
  2. A populáció minden egyedének elsődleges alkalmasságának megállapítása.
  3. Az algoritmus iterációinak leállítási feltételeinek ellenőrzése.
  4. A kiválasztási funkció segítségével.
  5. Genetikai operátorok alkalmazása.
  6. Új populáció létrehozása.
  7. A 2-6. lépéseket egy ciklusban ismételjük, amíg a szükséges feltétel teljesül, majd kiválasztjuk a leginkább alkalmazkodó egyedet.

Nézzük meg röviden az algoritmus kevésbé nyilvánvaló részeit. A munkaviszony megszüntetésének két feltétele lehet:

  1. Az iterációk száma.
  2. A megoldás minősége.

A genetikai operátorok a mutációs operátor és a keresztező operátor. A mutáció bizonyos valószínűséggel véletlenszerű géneket változtat meg. Jellemzően a mutáció valószínűsége alacsony számértékkel rendelkezik. Beszéljünk részletesebben a genetikai algoritmus „keresztező” eljárásáról. Ez a következő elv szerint történik:

  1. Minden L gént tartalmazó szülőpár esetében véletlenszerűen választjuk ki a Tski keresztezési pontot.
  2. Az első leszármazott az első szülő génjeinek összekapcsolásával jön létre [Tski+1; L] génjei a második szülőnek.
  3. A második gyermek fordított módon épül fel. Most az első szülő génjeit hozzáadjuk a második szülő génjeihez [Tski+1; L].

Triviális példa

Oldjuk meg a problémát egy genetikai algoritmus segítségével, a maximális egységszámú egyed keresésének példájával. Álljon egy egyed 10 génből. Állítsunk be egy nyolc egyedből álló elsődleges populációt. Nyilvánvalóan a legjobb személynek a 1111111111-esnek kell lennie. Hozzunk létre egy GA-t a megoldáshoz.

  • Inicializálás. Válasszunk ki 8 véletlenszerű személyt:

A táblázatból kitűnik, hogy a 3. és 7. egyedek a legnagyobb egységszámmal rendelkeznek, így a populáció legalkalmasabb tagjai a probléma megoldására. Mivel jelenleg nincs megfelelő minőségű megoldás, az algoritmus továbbra is működik. El kell végezni az egyének kiválasztását. Az egyszerűbb magyarázat kedvéért a kiválasztás véletlenszerűen történjen, és egy mintát kapunk az egyedekből (n7, n3, n1, n7, n3, n7, n4, n2) - ezek az új populáció szülei.

  • Genetikai operátorok használata. Ismét az egyszerűség kedvéért feltételezzük, hogy a mutáció valószínűsége 0. Más szóval, mind a 8 egyed úgy adja tovább a génjét, ahogy van. A keresztezés végrehajtásához véletlenszerűen egyedpárokat készítünk: (n2, n7), (n1, n7), (n3, n4) és (n3, n7). Az egyes párok keresztezési pontjai szintén véletlenszerűen kerülnek kiválasztásra:
  • Egy új, leszármazottakból álló populáció létrehozása:

A további intézkedések nyilvánvalóak. A GA-kkal kapcsolatban a legérdekesebb dolog az egyes populációk átlagos egységszámának becslése. Az első populációban átlagosan 5,375 egység volt egyedenként, a leszármazottak populációjában - 6,25 egység egyedenként. És ez a tulajdonság akkor is megfigyelhető, ha a mutációk és keresztezések során az első populációban a legtöbb egyedszámmal rendelkező egyed elveszik.

Megvalósítási terv

A genetikai algoritmus elkészítése meglehetősen összetett feladat. Először lépések formájában felsoroljuk a tervet, majd mindegyiket részletesebben elemezzük.

  1. Az ábrázolás meghatározása (ábécé).
  2. Véletlenszerű változási operátorok meghatározása.
  3. Az egyedek túlélésének meghatározása.
  4. Az elsődleges populáció generálása.

Az első szakasz kimondja, hogy az ábécé, amelybe egy megoldáshalmaz vagy egy sokaság minden elemét kódolják, kellően rugalmasnak kell lennie ahhoz, hogy egyszerre lehetővé tegye a véletlenszerű permutációk szükséges műveleteit és értékelje az elsődleges és az átment elemek alkalmasságát. változtatások. Matematikailag megállapították, hogy ideális ábécét ezekre a célokra nem lehet létrehozni, ezért ennek összeállítása az egyik legnehezebb és legkritikusabb szakasz a GA stabil működésének biztosításához.


Nem kevésbé nehéz a módosítási és létrehozási operátorok meghatározása. Sok operátor képes elvégezni a szükséges műveleteket. Például a biológiából ismert, hogy minden faj kétféleképpen szaporodhat: ivarosan (keresztezés) és ivartalanul (mutációk). Az első esetben a szülők genetikai anyagot cserélnek, a másodikban a szervezet belső mechanizmusai és a külső hatások által meghatározott mutációk fordulnak elő. Emellett a természetben nem létező reprodukciós modellek is használhatók. Például használja három vagy több szülő génjeit. A keresztezéshez hasonlóan sokféle mechanizmus beépíthető a genetikai mutációs algoritmusba.

A túlélés módszerének megválasztása rendkívül megtévesztő lehet. A genetikai algoritmusban számos módszer létezik a szelekcióra. És amint azt a gyakorlat mutatja, a „legrátermettebb túlélése” szabály nem mindig a legjobb. Bonyolult technikai problémák megoldása során gyakran kiderül, hogy sok átlagos vagy még rosszabb megoldás közül kerül ki a legjobb megoldás. Ezért gyakran elterjedt a valószínűségi megközelítés alkalmazása, amely azt állítja, hogy a legjobb megoldásnak nagyobb az esélye a túlélésre.


Az utolsó szakasz olyan rugalmasságot biztosít az algoritmus számára, amellyel senki más nem rendelkezik. A megoldások elsődleges populációja beállítható bármely ismert adat alapján, vagy teljesen véletlenszerűen úgy, hogy egyszerűen átrendezi a géneket az egyedeken belül, és véletlenszerű egyedeket hoz létre. Azonban mindig érdemes megjegyezni, hogy az algoritmus hatékonysága nagymértékben függ a kezdeti sokaságtól.

Hatékonyság

Egy genetikai algoritmus hatékonysága teljes mértékben a tervben leírt lépések helyes végrehajtásától függ. Itt különösen nagy hatást gyakorol az elsődleges populáció létrehozása. Ennek számos megközelítése létezik. Leírunk néhányat:

  1. Egy teljes populáció létrehozása, amely egy adott területen az egyedek összes lehetséges változatát tartalmazza.
  2. Véletlenszerűen generáljon egyéneket az összes érvényes érték alapján.
  3. Pont véletlenszerű egyed létrehozása, amikor az elfogadható értékek közül kiválasztunk egy generációs tartományt.
  4. A populáció létrehozásának első három módszerének kombinálása.

Ebből arra következtethetünk, hogy a genetikai algoritmusok hatékonysága nagymértékben függ a programozó e téren szerzett tapasztalatától. Ez a genetikai algoritmusok hátránya és előnye is.



Előző cikk: Következő cikk:

© 2015 .
Az oldalról | Kapcsolatok
| Oldaltérkép