Bás

Használható segédanyagok: Haskell könyvtárainak dokumentációja, Hoogle, a tárgy honlapja és a BE-AD rendszerbe feltöltött beadandók. Ha bármilyen kérdés, észrevétel felmerül, azt a felügyelőknek kell jelezni, NEM a diáktársaknak!

Tekintve, hogy a tesztesetek, bár odafigyelés mellett íródnak, nem fedik le minden esetben a függvény teljes működését, határozattan javasolt még külön próbálgatni a megoldásokat beadás előtt, vagy megkérdezni a felügyelőket!

Részpontszámokat csak az elégséges szint elérése után lehet kapni!

A feladat összefoglaló leírása

Ebben a feladatban a magyar nevén ,,Bás’’-nak hívott kockajáték játékmeneteinek rögzítésére és elemzésére szolgáló függvényeket kell megvalósítani.

A játékszabály a következő: tetszés szerinti számú játékos egymás után dob két kockával. A dobás eredményét csak a dobó játékos láthatja, a többiek nem. A dobás után közölni kell az eredményt a következő formában: ha dobott számok különbözőek, akkor a nagyobbik szám tízszereséhez hozzáadjuk a kisebbik számot és az így kapott összeget közöljük. Ha a dobott számok egyenlőek, akkor bást értünk el. Ezután a soron következő játékos dönt arról, hogy elhiszi a bejelentést, vagy nem. Ha igen, akkor ő következik dobásra. Ha nem hiszi el, akkor az kap hibapontot, akinek nem volt igaza. Lényeges szabály, hogy mindig csak az előző mondásnál értékesebb mondást lehet bejelenteni.

A dobások értéke növekvő sorrendben: 31, 32, 41, 42, 43, 51, 52, 53, 54, 61, 62, 63, 64, 65, 1-es bás, 2-es bás, 3-as bás, 4-es bás, 5-ös bás, 6-os bás, és végül a 21.

Segítségül a következő típusokat fogjuk majd használni:

type DoubleRoll = (Int,Int)
data RollResult
   = Simple Int -- ha különbözőek a számok (és nem a 21 jön ki belőlük)
   | Bas Int    -- ha két egyforma számot dobunk (,,bás'')
   | TwentyOne  -- ha 1-est és 2-est dobunk
     deriving (Eq, Show, Ord, Data, Typeable)

Eredmény képzése dobásból (2 pont)

Adott egy DoubleRoll típusú érték. Alakítsuk RollResult típusúvá a fenti szabályok szerint!

toResult :: DoubleRoll -> RollResult

Test>
Simple 64 :: RollResult
Test>
Simple 64 :: RollResult
Test>
Bas 3 :: RollResult
Test>
TwentyOne :: RollResult
Test>
Simple 31 :: RollResult

A dobás szabályosságának ellenőrzése (2 pont)

Adott egy RollResult típusú érték. Ellenőrizzük, hogy 2 dobókocka segítségével valóban kidobható-e az adott eredmény!

Segítség:

isRegularResult :: RollResult -> Bool

Test>
False :: Bool
Test>
True :: Bool
Test>
False :: Bool
Test>
True :: Bool
Test>
False :: Bool
Test>
True :: Bool

Igaz-e a bemondás? (1 pont)

Adott egy dobás (amelyet a többiek nem láthatnak), és az eredmény, amelyet a dobó játékos bemondott. Döntsük el, hogy igazat mondott-e!

correspondsTo :: DoubleRoll -> RollResult -> Bool

Test>
False :: Bool
Test>
True :: Bool
Test>
False :: Bool
Test>
True :: Bool

Szabályos-e a következő bemondott eredmény? (1 pont)

Adott két egymás utáni bemondott eredmény. Döntsük el, hogy a második eredmény valóban nagyobb értékű-e az elsőnél! (A sorrendet lásd az általános leírásnál.) Feltételezhetjük, hogy a RollResult értékek önmagukban szabályosak.

isToppedBy :: RollResult -> RollResult -> Bool

Test>
True :: Bool
Test>
True :: Bool
Test>
True :: Bool
Test>
False :: Bool

Szabályos-e bemondások egy sorozata? (2 pont)

Egy listában ábrázoljuk az egymás utáni eredmény-bemondásokat. Adjunk meg egy függvényt, amely képes eldönteni, hogy szabályos-e a sorozat, azaz mindig az előzőnél értékesebb eredményt mondtak-e be a játékosok! Itt is feltételezhetjük, hogy a RollResult értékek önmagukban szabályosak.

isValid :: [RollResult] -> Bool

Test>
True :: Bool
Test>
True :: Bool
Test>
False :: Bool
Test>
False :: Bool
Test>
False :: Bool

Egy játékmenet leghosszabb ,,igazmondó’’ szakasza (3 pont)

Adott egy lista, amely rendezett párokban tartalmazza az egyes dobásokat és a hozzájuk tartozó bemondott eredményeket a játék menetének sorrendjében. Az így reprezentált játékmenetre bevezetjük a következő típusszinonímát:

type GamePlay = [(DoubleRoll, RollResult)]

Példa játékmenetekre:

play1 :: GamePlay
play1 = [((3,2), Simple 32), -- I
         ((1,3), Simple 42), -- H
         ((3,4), Simple 43), -- I
         ((4,5), Simple 54), -- I
         ((4,2), Bas 4),     -- H
         ((5,5), Bas 5),     -- I
         ((3,3), TwentyOne)] -- H

play2 :: GamePlay
play2 = [((3,2), Simple 32), -- I
         ((4,3), Simple 43), -- I
         ((4,5), Simple 54), -- I
         ((2,4), Bas 2),     -- H
         ((4,4), Bas 4),     -- I
         ((1,2), TwentyOne)] -- I

Definiáljunk egy függvényt, amely visszaadja, hogy egy adott játékmenetben milyen hosszú volt az a leghosszabb szakasz, amikor mindenki egymás után igazat mondott (tehát a dobott és a bemondott érték megegyezett)!

longestTruthful :: GamePlay -> Int

Test>
2 :: Int
Test>
3 :: Int

Ki a legtöbbet hazudó játékos? (4 pont)

Adott a játékosok száma (n) és egy játékmenet. A játékosokat 1-től n-ig sorszámozzuk, a játékot az 1-es sorszámú játékos kezdte, aztán a 2-es, stb. Amikor már mindenki sorra került, újból az 1-es játékos dobott. A függvény annak a játékosnak a sorszámát adja vissza, aki a legtöbbször hazudott a játékmenet során.

biggestLiar :: Int -> GamePlay -> Int

Test>
1 :: Int
Test>
2 :: Int
Test>
2 :: Int
Test>
1 :: Int
Test>
4 :: Int

Tipp: Készíts egy segédfüggvényt, amely a párokat átalakítja logikai értékekké, attól függően, hogy igaz volt-e a bemondás, és minden logikai érték mellé hozzárendeli a játékos sorszámát!

Pontozás