PlanetFight Készítők: A játékot készítette Róth Gergő (roth@dcs.uni-pannon.hu) és Orosz Ákos (orosz@dcs.unipannon.hu). Esetleges kérdésekkel hozzájuk lehet fordulni. Rövid leírás: A játék célja minél több bolygó elfoglalása a térképen, a bolygó méreteit és a bolygók közti távolságokat figyelembe véve. Egy térképen egyszerre két játékos játszik egymással versenyezve. Szabályrendszer: Cél: Bolygók elfoglalásával több pontot kell szerezni a játék végére, mint amennyit az ellenfél szerez. Természetesen nem minden bolygó egyforma nagy, és a nagyobb bolygókon több nyersanyag van, így ha valaki nagyobb bolygót birtokol, akkor az több pontot ér. A térképen megtalálható minden olyan bolygópár közötti távolság, ahol bolygóközi utazás lehetséges. Két bolygó közt az utazás annyi körig tart, amennyi a bolygók közti távolság (például ha két bolygó távolsága 3, akkor az űrhajó az utat 3 kör alatt teszi meg). Minden játékosnak van valamennyi űrhajója, amikkel képesek elfoglalni még fel nem fedezett, neutrális bolygókat. A játékosok utasításokat adhatnak a saját hajóiknak. Természetesen a hajópilóták is rendelkeznek némi intelligenciával, így lehetetlen kéréseket nem fognak végrehajtani. Amennyiben a hajó éppen egy bolygón tartózkodik, úgy a pilóta bárhova szívesen elindul. Ha a hajó két bolygó közötti úton van, akkor a pilóta legfeljebb visszafordulni hajlandó, de ezt csak egyszer tudja megtenni. Amennyiben egy hajó az ellenfél bolygójára téved, úgy azonnal visszafordul arra a bolygóra, amelyről jött. Amennyiben két vagy több ellenséges hajó ugyanarra a neutrális bolygóra téved, akkor mindegyik visszafordul. A játék meghatározott számú körből áll, minden egyes körben minden játékos léphet az összes saját hajójával. A játék vége: A játék végén az elfoglalt bolygók pontszámai játékosonként adódnak össze. A játék akkor ér véget, ha nincs több neutrális bolygó, vagy ha elfogy a körök száma.
Kommunikáció a PlanetFight programmal A PlanetFight program feladata két mesterséges, illetve valódi intelligencia kezelése. Egy intelligencia lehet a játékos által megírt program és a játékos is. Ezeknek az intelligenciáknak az interakcióit a PlanetFight program váltakozva kezeli, úgy, hogy minden körben minden egyes intelligencia léphet. A kommunikáció a játékosok által megírt programokkal a standard input és a standard outputon keresztül történik. A standard error használható debug üzenetek írására. A PlanetFight biztosítja a játékos által megírt programnak a standard input-on a teljes térképet és az összes játékos összes hajójának az aktuális helyzetét, illetve mozgását. Ahol játékos azonosító szerepel, ott az 1 érték jelöli az első, a 2 érték a második játékost. A 0 érték a tulajdonos nélküli objektumokat jelenti. Csak bolygó lehet tulajdonos nélküli, vagyis neutrális. A PlanetFight a bolygók közti távolságokat egy gráfon reprezentálja, ahol a gráf csúcsai az egyes bolygók. A gráf irányítatlan. A bolygók sorszámozása 0-tól kezdődik és n-1-ig tart. Kapcsolati mátrix: olyan mátrix, mely egy gráf csúcsai közti kapcsolat értékét tárolja. Mindig négyzetes mátrix. A mátrix i-ik oszlopa és j-ik sora tárolja az i-ik csúcsból a j-ik csúcsba tartó él súlyát. Mivel a gráf irányítatlan, így a gráf transzponáltja megegyezik önmagával. A PlanetFight esetében minden nem pozitív súly végtelen súlyt jelent, vagyis a két csúcs között nincs él. A standard input-ra küldött információk sorrendben: - Bolygók száma -> n: egész szám - Jelenlegi játékos azonosítószáma -> i: egész szám - n sor információ a bolygóról, minden sorban: o a bolygó tulajdonosa: egész szám o a bolygó mérete: egész szám - nxn dimenziós mátrix, mely a bolygók kapcsolati gráfját reprezentálja: egész számok mátrixa - Játékosonkénti hajók számát -> s: egész szám - s sor információ az első játékos hajóiról, minden sorban: o kiinduló bolygó: egész szám o célbolygó: egész szám o milyen messze van még a célbolygótól: egész szám - s sor információ a második játékos hajóiról ugyanolyan formában, mint az első játékos esetében - hátralevő körök száma: egész szám A játékos által megírt program a standard output-on keresztül biztosít információt a PlanetFightnak, így a standard output-ra tilos bármilyen más szöveget kiírni. A mesterséges intelligenciának
utasítást kell adnia a hozzá tartozó hajóknak. Ha nem ad utasítást, akkor a hajó folytatja elkezdett útját, vagy ha egy bolygón van, akkor ott is marad. Tehát a mesterséges intelligencia kimenetének sorokból kell állnia, minden egyes sorban két számot kell kiíratnia egymástól szóközzel, vagy tabulátorral elválasztva. Az első szám a hajó azonosítószáma, a második szám pedig annak a bolygónak az azonosítószáma, amire a hajót a játékos küldeni akarja. Amennyiben a hajó olyan utasítást kap, amit nem tud végrehajtani, úgy a pilóta úgy veszi, mintha nem kapott volna semmilyen utasítást, vagyis folytatja előzőleg megkezdett tevékenységét. Pár példakimenet: 0 3 : a 0. sorszámú hajót a 3-as sorszámú bolygóra küldi 2 1 : a 2. sorszámú hajót az 1-es sorszámú bolygóra küldi 1-1 : érvénytelem parancs, nincs ilyen sorszámú bolygó -2 1 : érvénytelen parancs, nincs ilyen sorszámú hajó A játékosok debug üzeneteket a standard error-ra írhatnak (pl. fprintf(stderr, debug information ) ). Az fprintf használata hasonló a printf-hez, a különbség annyi, hogy első paraméternek meg kell adni egy FILE mutatót, jelen esetben ez stderr. Példabemenet a játékos által megírt program számára: Kezdőállapot: 10 // bolygók száma 2 // a 2-es játékos programja fut 2 1 // 0. bolygó: tulajdonos: 2, méret: 1 0 1 // 1. bolygó: tulajdonos: 0, méret: 1 0 2 // 2. bolygó: tulajdonos: 0, méret: 2 0 2 // 3. bolygó: tulajdonos: 0, méret: 2 0 3 // 4. bolygó: tulajdonos: 0, méret: 3 0 3 // 5. bolygó: tulajdonos: 0, méret: 3 0 5 // 6. bolygó: tulajdonos: 0, méret: 5 0 5 // 7. bolygó: tulajdonos: 0, méret: 5 1 1 // 8. bolygó: tulajdonos: 1, méret: 1 0 1 // 9. bolygó: tulajdonos: 0, méret: 1 0 2 3 6 5 6 6 6 4 0 // kapcsolati gráf 2 0 4 5 5 4 0 6 3 0 3 4 0 5 4 0 3 5 6 0 6 5 5 0 2 4 0 3 4 3 5 5 4 2 0 5 6 2 5 3 6 4 0 4 5 0 0 6 2 4
6 0 3 0 6 0 0 5 0 0 6 6 5 3 2 6 5 0 6 4 4 3 6 4 5 2 0 6 0 5 0 0 0 3 3 4 0 4 5 0 1 // játékosonkénti hajók száma 3 3 0 // az első játékos hajója a 3-as bolygón állomásozik 4 4 0 // a második játékos hajója a 4-es bolygón // állomásozik, mivel az aktuális játékos a 2-es, ezért // csak ennek a hajónak tud parancsokat adni 39 // hátralevő körök száma Következő állapot: 10 2 2 1 0 1 0 2 0 2 0 3 0 3 0 5 0 5 1 1 0 1 0 2 3 6 5 6 6 6 4 0 2 0 4 5 5 4 0 6 3 0 3 4 0 5 4 0 3 5 6 0 6 5 5 0 2 4 0 3 4 3 5 5 4 2 0 5 6 2 5 3 6 4 0 4 5 0 0 6 2 4 6 0 3 0 6 0 0 5 0 0 6 6 5 3 2 6 5 0 6 4 4 3 6 4 5 2 0 6 0 5 0 0 0 3 3 4 0 4 5 0 1 3 9 2 // mindkét hajó ugyanarra a bolygóra repül, ha mindketten odaérnek, akkor visszafordulnak 4 9 2 38 Következő állapot: 10 2 2 1 0 1
0 2 0 2 0 3 0 3 0 5 0 5 1 1 0 1 0 2 3 6 5 6 6 6 4 0 2 0 4 5 5 4 0 6 3 0 3 4 0 5 4 0 3 5 6 0 6 5 5 0 2 4 0 3 4 3 5 5 4 2 0 5 6 2 5 3 6 4 0 4 5 0 0 6 2 4 6 0 3 0 6 0 0 5 0 0 6 6 5 3 2 6 5 0 6 4 4 3 6 4 5 2 0 6 0 5 0 0 0 3 3 4 0 4 5 0 1 3 3 0 // az első játékos meggondolta magát, a hajóját visszafordította 4 9 1 37 A PlanetFight level (.pflvl) fájltípus A PlanetFight pályáit.pflvl fájltípus tárolja. Ha a felhasználó ad meg pályát ( Level melletti Browse gomb), akkor a start game -re kattintva a megadott pálya töltődik be, amennyiben ez nem sikerül, vagy nincs megadva fájl, akkor véletlenszerűen generál egy pályát a véletlenszerű beállításoknak megfelelően. A pálya tárolja a bolygókat azok kapcsolati gráfjával együtt, valamint tárolja a hajók kezdeti pozícióit. A bolygók pozíciói bármilyen értéket felvehetnek, a kirajzolt térkép mérete alkalmazkodik a bolygók helyzetéhez. Példa egy.pflvl fájlra (// után kommentek, nem a fájl része): 4 // bolygók száma 34 52 5 2 // 0. bolygó x koordinátája, y koordinátája, mérete, tulajdonosa 89 15 10 0 // 1. bolygó x koordinátája, y koordinátája, mérete, tulajdonosa 57 76 7 0 // 2. bolygó x koordinátája, y koordinátája, mérete, tulajdonosa 2 100 15 1 // 3. bolygó x koordinátája, y koordinátája, mérete, tulajdonosa 0 2 3 4 // az 1. és a 0. bolygó közt 2, a 2. és a 0. közt 3, a 3. és a 0. közt 4 a távolság 2 0 4 3 // a 0. és az 1. bolygó közt 2, a 2. és az 1. közt 4, a 3. és az 1. közt 3 a távolság 3 4 0 3 // a 0. és a 2. bolygó közt 4, az 1. és a 2. közt 3, a 3. és a 2. közt 3 a távolság 4 3 3 0 // a 0. és a 3. bolygó közt 4, az 1. és a 3. közt 3, a 2. és a 3. közt 3 a távolság
2 // játékosonkénti hajók száma 1 3 3 0 // hajó tulajdonosa, kezdőbolygója, célbolygója, hány kör van még hátra a megérkezésig 1 3 2 1 // hajó tulajdonosa, kezdőbolygója, célbolygója, hány kör van még hátra a megérkezésig 2 0 0 0 // hajó tulajdonosa, kezdőbolygója, célbolygója, hány kör van még hátra a megérkezésig 2 0 1 1 // hajó tulajdonosa, kezdőbolygója, célbolygója, hány kör van még hátra a megérkezésig 40 // a körök száma, ennyi kör után a játék leáll A PlanetFight program kezelése Telepítés (Windows alatt): a mellékelt könyvtárstruktúrát mentsük el. A PlanetFight programot a PlanetFight.exe indítja. Telepítés (Linux alatt): a mellékelt könyvtárstruktúrát mentsük el. A PlanetFight programot a PlanetFight.sh indítja. A játék megkezdéséhez meg kell adni a két játékos programját a megfelelő mezőben ( Player1 és Player2 melletti Browse gomb). Értelemszerűen ez a program Windows-on egy.exe fájl, míg Linuxon egy futtatható állomány. Amennyiben a felhasználó nem ad meg valamelyik Playernek programot, úgy a megfelelő Player körében a felhasználónak kell cselekednie. A felhasználó a hajóknak az egér bal gombjával tud parancsot adni. Egy bolygón az egér bal gombját lenyomva tartva, majd onnét egy másik bolygóra húzva és felengedve, a program kiválaszt az induló bolygóról egy hajót, aminek azt a parancsot adja, hogy repüljön a célbolygóra. Minden már parancsot kapott hajó eltűnik a képernyőről. Amennyiben a felhasználó mégis látni akarja a hajókat, úgy a térkép alatt található felfele irányuló háromszögre kattintva kiválaszthatja a parancsokat teljesítő hajókat, amik így láthatóvá válnak. Kiválasztva egy parancsot teljesítő hajót, törölni lehet a parancsot, vagy ha a hajó éppen úton van, akkor vissza lehet fordítani a hajót.
Jobb egérgombbal kattintva egy hajón vagy egy bolygón, kiírja az objektumnak az adatait. Bolygók esetében: az azonosítóját, a tulajdonosát és a méretét. Hajók esetében: az azonosítóját, az induló bolygóját, a célbolygóját (ha éppen egy bolygón állomásozik, akkor a kettő ugyanaz), azt hogy hány kör van még az érkezésig (állomásozó hajó esetén 0) és a tulajdonosát. A File menü start game pontjára kattintva kezdődik el a játék. A pályát még a játék megkezdése előtt meg kell adni a Level alatti beviteli mezőben. Amennyiben a felhasználó nem ad meg pályát, úgy a PlanetFight generál egyet véletlenszerűen a Random map options beállításainak megfelelően. Az Options menü show process output alpontjára kattintva a felhasználó megnézheti, hogy mit ír ki a futtatandó program az stdout-ra és az stderr-re. Véletlenszerű bolgyó beállítási lehetőségei: Number of planets: bolygók száma Number of ships per player: játékosonkénti hajók száma Maximum travelling distance: a hajók legfeljebb milyen messzire közlekedhetnek; minél nagyobb, annál sűrűbb a bolygók kapcsolati gráfja Maximum planet size: a bolygók maximális mérete
Distance scale: a bolygók valós távolságát a program leosztja ezzel az értékkel; az érték növelésével a növelhető a bolygók kapcsolati gráfjának a sűrűsége Round limit: legfeljebb hány körig tarthat a játék Mellékelt programok random.c / random.exe (Windows) / random (Linux): egyszerű program, mely illusztrálja a kommunikációt a PlanetFight programmal. A program logikája nagyon egyszerű: minden hajót elküld egy véletlenszerűen kiválasztott bolygóra. uber.exe (Windows) / uber (Linux): kicsivel okosabb logikájú program. A beadott pályaműveknek ezt ajánlatos legyőzni. Forráskód nincs mellékelve. Értékelés A verseny során különböző (előre nem ismert) pályákon zajlik majd a küzdelem körmérkőzések formájában a pályázók programjai között. A programok egymás ellen fognak játszani
egy automata segítségével, amelynek szabályai hasonlóak a kiadott egyszerűbb PlanetFight programéhoz. A futtatás során egy lépésre maximum 2 másodperc ideje lesz a programoknak, ennél hosszabb gondolkodási idő esetén a mérkőzést lebonyolító program úgy értelmezi, hogy a program nem akarja a hajókat irányítani. Az egyes fordulókban szerzett pontszámok összeadódnak, a legtöbb pontot szerzett program lesz a győztes.