HTML

Survive Developement

Itt olvashatod a Survive! nevű játék fejlesztésének állapotát, lépéseit. És mi is lesz a játék? Egy zombis-túlélős játék, ahol elsősorban a csapatmunkára építkezve kell megpróbálni életben maradni egy kihalt városban. A terep teljesen a tietek, nincsenek szabályok: éljetek túl, ahogy tudtok!


Küldj e-mailt nekünk:
gilgamesco@gmail.com

Sikolyok

Ettől tépjük a hajunkat:

Friss topikok

  • Sir Butcher: A gyors mozgású ütközés-érzékelés majd a lövésnél lesz topic :D A második esetben teljesen igaza... (2012.04.05. 16:38) Ütközésérzékelés
  • _fpeti_: Halad ez. (2012.04.04. 22:01) Gravitáció
  • Sir Butcher: Az sem rossz, az tény :D Szerencsére egyelőre annyi különbözőt kell csinálnom, hogy esélyem sincs ... (2012.02.20. 21:48) Scenery - Még több látvány
  • Sir Butcher: Na, ideírom: obj-nél megoldottam a csontokat. Melléktermékként összejöttek, extra számítás nélkül ... (2011.12.02. 11:48) Model Animálás - a probléma, és a (vélt) megoldás
  • Burwor: "A tesztvárosban sétálgatva belefutsz egy házba, aminek hiányzik egy fala. Mit csinálsz?" Zárva a... (2011.11.10. 15:00) Sziduri - a grafmotor bemutatkozik

unsafeShootYourselfInFoot

2011.09.07. 09:32 :: GizmoSDK

Nos, igen. Én is engedtem a sötét oldal csábításának. Bár, erre igazából büszke vagyok :D No de miről is van szó? Épp neki akartam állni debuggolni a programomat, amikor jött a hidegzuhany: itt én nem fogok debug printeket kiírni. Legalábbis úgy nem, ahogy eddig.

 

A probléma a következő: a Haskell nyelvben élesen el vannak választva a mellékhatásos és a mellékhatás nélküli függvények. Mellékhatás nélkülinek hívunk egy függvényt akkor, ha nem változtatja meg a környezete állapotát, miközben lefut. Ilyen mondjuk a matematikában használatos szinusz függvény: megkap egy számot, és visszaad egy másikat. Nem ír ki közben a terminálra semmit, nem indítja el a nyomtatót, nem olvasztja le a hűtőt, és nem vesz le pénzt a számládról (különben kevesen használnák :D). Na, a mellékhatásos függvények mindezt megtehetik. (Ebből már világosan látnia kell mindenkinek, hogy a mellékhatásos függvény a sátán műve :D) Valamint a mellékhatásos függvények meghívhatnak mellékhatás nélküli függvényeket és más mellékhatásos függvényeket is, míg a mellékhatás nélküli függvények csak mellékhatás nélküli függvényeket hívhatnak meg. Ez önmagában még nem lenne gond. Általában a Haskell programok 80%-a mellékhatás nélküli számítás, ami azért jó, mert egyrészt könnyebben párhuzamosítható, hiszen ezek a függvények nagyon jól elvannak egy-egy szálban, nem nyúkálnak a többihez. Másrészt pedig sokkal könnyebb belátni róluk, hogy helyesek, mivel nem függnek láthatatlan paraméterektől (igen, rád gondolok, globális változó!). A maradék 20% pedig végzi a piszkos munkát (IO, ilyesmik).

 

A probléma ott kezdődik, hogy ha valaki debuggolni akarja a progit. Elindítottam a programot, és nem akar leállni. Gyanítom, egy végtelen ciklusba keveredett. Szeretném, ha minden függvény kiírná, hogy őt most épp meghívták. Tehát azok a mellékhatás nélküli függvények, amik a program zömét teszik ki, mellékhatást kell okozniuk. Dehát ezt nem lehet! Na, ilyenkor mi a teendő?

 

Több megoldás közül választhatunk. Az egyik, hogy elsőre jól írjuk meg a kódot, és akkor nem kell debuggolni :D De ez túl egyszerű, lássuk be. Meg, akit órabérben fizetnek, tudja, hogy ez nem járható út :D A második lehetőség, hogy fáradságos munkával a függvények típusát átírjuk úgy, hogy mellékhatásos legyen, majd, ha sikerült kijavítani a hibát, visszaírjuk. Fárasztó rabszolgamunka. A harmadik, hogy használunk egy előre megírt könyvtárat (ilyen a hslogger), ami szép átgondolt keretrendszert kínál a számunkra. (Ez a javasolt megoldás.) De ez most nekem nem jó, mivel egyrészt időhiányban vagyok, másrészt nincs is szükségem ilyen komoly berendezésre. Ekkor jön a negyedik módszer, amit gyakorlatilag simán nevezhetünk hack-nek. Ugyanis elhitetjük a fordítóval, hogy a függvényünk, ami mellékhatásos, igazából nem mellékhatásos. Ezt úgy lehet megtenni, hogy lassan a fordító felé fordulsz, mélyen a szemébe nézel, majd lassan, jól hallhatóan és tagoltan odasúgod neki, hogy "unsafePerformIO". Ekkor ő egyetértően bólogat, és komoly arccal nekikezd fordítani. :D

 

Mikor érdemes az unsafePerformIO-t használni? Amikor olyan mellékhatásokat akarunk a programba injektálni, amiről biztosak vagyunk, hogy nem okoznak összeakadást. Ilyen pl. a debugprint az esetemben, mert soha nem lesz szükségem a terminálon szereplő dolgokra. Vagy használhatjuk olyankor is, amikor optimalizálni akarunk egy algoritmust (lásd: ByteString). De igazából ezt csak akkor szabad használni, ha tudod, mit csinálsz.

 

U.i.: Akarok egy ilyen pólót. (A felirat rajta: "Haskell Hackers - We're not afraid of a little unsafePerformIO!")

U.i.2.: Ha valaki esetleg Haskellban programozik, és nem tudna rájönni, hogy hogy is kell ezt megvalósítani, annak itt egy kis példakód:

import System.IO.Unsafe

debugIO :: IO a -> b -> b
debugIO a b = unsafePerformIO $ a >> return b

debugPrint :: String -> a -> a
debugPrint s a = debugIO (putStrLn s) a

Aztán, ha használni is akarod, akkor ilyen formában tudod megtenni:

add :: Int -> Int -> Int
add n1 n2 = debugPrint "Hello, world!" (n1 + n2)

Arra mindenesetre vigyázni kell, hogy az ilyen módon mellékhatásmentesített függvényekre is vonatkoznak a lusta kiértékelés szabályai, illetve ezek is ugyanúgy oiptimalizálva lesznek a fordító által, mint a többi mellékhatásmentes függvény, tehát semmi garancia nincs arra nézve, hogy lefut a kód. Erre problémára a strictness operátorokat javaslom.

2 komment

Címkék: debug unsafeperformio haskell hajtépés

A bejegyzés trackback címe:

https://survivedev.blog.hu/api/trackback/id/tr403208319

Kommentek:

A hozzászólások a vonatkozó jogszabályok  értelmében felhasználói tartalomnak minősülnek, értük a szolgáltatás technikai  üzemeltetője semmilyen felelősséget nem vállal, azokat nem ellenőrzi. Kifogás esetén forduljon a blog szerkesztőjéhez. Részletek a  Felhasználási feltételekben és az adatvédelmi tájékoztatóban.

Sir Butcher · http://survivedev.blog.hu/ 2011.09.07. 18:17:05

Szerintem sokkal hatékonyabb lenne azt mondani a fordítónak, hogy "Bubu, te madár vagy!"

(Plusz 10 pont annak, akinek a leghaloványabb tippje is van arról, hogy ez mit jelent :P

GizmoSDK 2011.09.07. 18:20:19

unsafeBubuYouAreABird... ahha. És gondolom, kell a progi elejére az

import YogiBear

rész is. Oké, mjad írok a Haskell fejlesztőinek :D
süti beállítások módosítása