Seznamy a n-tice  4. května 2023

Materiály

Nejste účastníkem kurzu
Pro zápis do kurzu se nejprve přihlašte a následně použijte tlačítko v přehledu kurzu.

Domácí projekty

Pojďme si procvičit práci se seznamem.

Některé z projektů – a zvlášť ten poslední – potřebují trochu přemýšlení; nebudeš-li vědět, jak dál, požádej na Discordu o radu!

0.

Napiš funkci vytvor_seznam_zvirat(), která vytvoří nový seznam domácích zvířat a vrátí ho. Domácí zvířata známe tato: "pes", "kočka", "králík", "had".

Tuto funkci použiješ pro otestování dalších úloh. Nehledej v ní nic složitého.

Příklad:

>>> vytvor_seznam_zvirat()
['pes', 'kočka', 'králík', 'had']

Každé zavolání funkce by mělo vytvořit nový, nezávislý seznam. Vyzkoušej si to následujícím „dialogem“:

>>> from moje_reseni import vytvor_seznam_zvirat
>>> zvirata = vytvor_seznam_zvirat()
>>> zvirata.pop()
'had'
>>> vytvor_seznam_zvirat()
['pes', 'kočka', 'králík', 'had']
>>> zvirata
['pes', 'kočka', 'králík']
1.

Napiš funkci filtruj_kratka_jmena, která dostane seznam řetězců a vrátí seznam těch, které jsou kratší než 5 písmen.

Například:

>>> from moje_reseni import vytvor_seznam_zvirat, filtruj_kratka_jmena
>>> zvirata = vytvor_seznam_zvirat()
>>> filtruj_kratka_jmena(zvirata)
['pes', 'had']

Vzpomeň si, jak se vytváří seznam: začni s prázdným seznamem a postupně přidávej prvek po prvku.

Funkce by měla opět vracet nový seznam a svůj argument nechat nezměněný. Vyzkoušej si to následujícím „dialogem“:

>>> from moje_reseni import vytvor_seznam_zvirat, filtruj_kratka_jmena
>>> zvirata = vytvor_seznam_zvirat()
>>> filtruj_kratka_jmena(zvirata)
['pes', 'had']
>>> zvirata
['pes', 'kočka', 'králík', 'had']
2.

Napiš funkci filtruj_k, která dostane seznam řetězců a vrátí seznam těch, které začínají na k.

Například:

>>> from moje_reseni import vytvor_seznam_zvirat, filtruj_k
>>> zvirata = vytvor_seznam_zvirat()
>>> filtruj_k(zvirata)
['kočka', 'králík']

Funkce by měla opět vracet nový seznam a svůj argument nechat nezměněný.

3.

Napiš funkci obsahuje, která dostane seznam a slovo a zjistí, jestli je to slovo v daném seznamu. Podle toho vrátí True nebo False.

Například:

>>> from moje_reseni import vytvor_seznam_zvirat, obsahuje
>>> zvirata = vytvor_seznam_zvirat()
>>> obsahuje(zvirata, 'pes')
True
>>> obsahuje(zvirata, 'vodováha')
False
4.

Napiš funkci bez_prvniho, která dostane seznam jmen a vrátí seznam se všemi jeho prvky kromě prvního.

>>> from moje_reseni import vytvor_seznam_zvirat, bez_prvniho
>>> zvirata = vytvor_seznam_zvirat()
>>> zvirata
['pes', 'kočka', 'králík', 'had']
>>> bez_prvniho(zvirata)
['kočka', 'králík', 'had']

Funkce by opět neměla změnit původní seznam:

>>> zvirata
['pes', 'kočka', 'králík', 'had']

A měla by fungovat i pro prázdný seznam:

>>> bez_prvniho([])
[]
5.

Složitější, nepovinný úkol!

Had byl pyšný na to, že je v abecedě první. Dokud nepřiletěla "andulka".

Abys hada uklidnila, vytvoř funkci serad_od_druheho, která zvířata seřadí podle abecedy, ale bude ignorovat první písmeno. Například:

>>> from moje_reseni import vytvor_seznam_zvirat, serad_od_druheho
>>> zvirata = vytvor_seznam_zvirat()
>>> serad_od_druheho(zvirata)
["had", "pes", "andulka", "kočka", "králík"]
>>> # (barvy jsou tu jen pro přehlednost, váš program vypisuje bez barev)

Máš tady seznam hodnot, které chceš seřadit podle nějakého klíče. Klíč se dá z každé hodnoty vypočítat – v našem případě je to hodnota kromě prvního písmenka (tedy od druhého písmenka dál).

Postup:

  • Vytvoř seznam dvojic (klíč, hodnota).
  • Seřaď tento seznam dvojic – dvojice se řadí nejdřív podle prvního prvku, pak druhého atd.
  • Nakonec vytvoř ze seznamu dvojic výsledný seznam hodnot.

Vytvoření seznamu se dělá tak, že začneš s prázdným seznamem a postupně do něj přidáváš hodnoty jednu po druhé.

6.

Napiš funkci vytvor_balicek, která vrátí nový zamíchaný seznam hracích karet pro hru Prší. Každá položka seznamu bude (na rozdíl od balíčku ze setkání) dvojice hodnota-barva.

Hodnoty karet jsou 2-10, 'J', 'Q', 'K', 'A'. Barvy jsou '♥' '♦' '♠' '♣'. (Symboly si můžeš zkopírovat jako text. Nezobrazují-li se ti v příkazové řádce správně, použij místo nich S, K, P, +.)

Například:

>>> from moje_reseni import vytvor_balicek
>>> vytvor_balicek()
[(2, '♥'), (10, '♠'), ('A', '♣'), ...

Následující sada úkolů je nepovinná. Procvičuje seznamy a n-tice. Když ji uděláš, budeš mít další hru!

Úkoly dělej postupně; navazují na sebe.

7.

Úkol na procvičení a vzpomenutí. Už jsi ho jednou vyřešila.

Pomocí cyklů for a parametru end pro print napiš program, který postupně z jednotlivých 'X' vypíše:

X X X X X
X X X X X
X X X X X
X X X X X
X X X X X

„Z jednotlivých 'X'“ znamená, že každý print vypíše jen jedno X. Nepoužívej tedy např. print('X X X X X') ani print('X ' * 5).

8.

Úkol na procvičení a vzpomenutí. Už jsi ho jednou vyřešila.

Napiš program, který vypíše „tabulku“ s násobilkou.

0 0 0 0 0
0 1 2 3 4
0 2 4 6 8
0 3 6 9 12
0 4 8 12 16
9.

Napiš funkci, která dostane seznam souřadnic (párů čísel menších než 10, která určují sloupec a řádek), a vypíše je jako mapu: mřížku 10×10, kde na políčka která jsou v seznamu napíše X, jinde tečku. Například:

nakresli_mapu([(0, 0), (1, 0), (2, 2), (4, 3), (8, 9), (8, 9)])

X . . . . . . . . .
X . . . . . . . . .
. . X . . . . . . .
. . . . . . . . . .
. . . X . . . . . .
. . . . . . . . . .
. . . . . . . . . .
. . . . . . . . . .
. . . . . . . . . X
. . . . . . . . . .

Jak na to?

  • Vzpomeň si, jak se vypisuje tabulka: pomocí dvou cyklů for zanořených do sebe.
  • Pro každou buňku tabulky (tedy vevnitř v cyklu) si vytvoř dvojici radek_a_sloupec = (cislo_radku, cislo_sloupce).
  • Napiš X, pokud je dvojice radek_a_sloupec v seznamu. Jinak napiš ..

Slova jako „souřadice“ a „pozice“ bohužel vypadají v jednotném i množném čísle stejně. Aby ses nezamotala, doporučuju proměnnou s jednou dvojicí pojmenovat radek_a_sloupec a seznam několika takových dvojic seznam_souradnic.

10.

Napiš funkci pohyb, která dostane seznam souřadnic a světovou stranu ("s", "j", "v" nebo "z"), a přidá k seznamu poslední bod „posunutý“ v daném směru. Např.:

seznam_souradnic = [(0, 0)]
pohyb(seznam_souradnic, 'j')
print(seznam_souradnic)         # → [(0, 0), (1, 0)]
pohyb(seznam_souradnic, 'j')
print(seznam_souradnic)         # → [(0, 0), (1, 0), (2, 0)]
pohyb(seznam_souradnic, 'v')
print(seznam_souradnic)         # → [(0, 0), (1, 0), (2, 0), (2, 1)]
pohyb(seznam_souradnic, 'z')
print(seznam_souradnic)         # → [(0, 0), (1, 0), (2, 0), (2, 1), (2, 0)]

Funkce by neměla nic vracet. Jen mění už existující seznam.

11.

Napiš cyklus, který se bude ptát uživatele na světovou stranu, podle ní zavolá pohyb, a následně vykreslí seznam jako mapu. Pak se opět se zeptá na stranu atd.

Začínej se seznamem [(0, 0), (0, 1), (0, 2)].

12.

Doplň funkci pohyb tak, aby při pohybu umazala první bod ze seznamu souřadnic. Výsledný seznam tak bude mít stejnou délku jako před voláním.

Jestli hraješ počítačové hry a víte co je WASD, můžeš změnit ovládání na tyto klávesy místo SZJV.

13.

Doplň funkci pohyb tak, aby zamezila:

  • pohybu ven z mapy,
  • pohybu na políčko, které už v seznamu je.

Vhodná výjimka pro tyto situace je ValueError('Game over').

14.

Teď máš hotový základ hry "Had"! Zkus si s ní chvíli hrát.

Pak přidej do hry hadí potravu.

Seznam jídla obsahuje na začátku dvě jídla na políčkách, na kterých není had (například: jidlo = [(2, 3), (4, 5)] znamená jedno jídlo na pozici (2, 3) a druhé na (4, 5)). Když had sežere jídlo, vyroste („nesmaže“ se mu ocas, tedy neprovede se to, co jsi přidali v předminulém úkolu) a na náhodném místě (kde není had) se přidá jídlo nové.

Na mapě se jídlo zobrazuje třeba jako otazník (?).

15.

Hadí hřiště může mít libovolné rozměry větší než 4×1. Třeba 20×20 nebo 10×30.

A nakonec projekt na přemýšlení.

16.

Zkus co nejjednodušeji udělat takový seznam, aby platilo:

seznam[5][5][5][5][5][5][5][5][5][5][5][5][5][5][5][5][5][5][0] == 5

Může seznam obsahovat sám sebe?