====== Cvičení 4: 1D pole ====== ==== Úkol 1 Opakování funkce a for cykly ==== * Napište program, který porovná dvě funkce ''a(x,y,z)'' a ''b(x,y,z)'' se třemi logickými proměnnými a zjistí, zda výrazy jsou ekvivalentní, případně vypíše pro jaké kombinace vstupů se výstupy liší. * Porovnejte následující funkce: def a(x,y,z): return (x and y) or (not y and z) def b(x,y,z): return x or z ==== Úkol 2 Najdi a změň ==== * Napište funkci ''my_find(a,b)'', která v řetezci ''a'' hledá řetězec ''b'' (nepoužívejte vestavěnou funkci find). * Pokud řetězec najde, vrátí index jeho prvního výskytu zleva. * Pokud řetězec nenajde, vrátí -1. * Napište funkci ''my_replace(a,b,c)'', která v řetězci ''a'' nahradí všechny výskyty řetězce ''b'' řetězcem ''c''. * Ve funkcích používejte pouze funkce * ''len(s)'' - délka řetězce, * ''s[i]'' - znak na pozici ''i'', * ''s[i:j]'' - podřetezec od ''i'' do ''j'' * ''s[:j]'', ''s[i:]'' - podřetězec od počátku do ''j'', resp. od ''i'' do konce. ==== Úkol 3 Záměna slova ==== * Napište program, který čte standardní vstup a v načteném řetězci zamění slovo ''Ahoj'' za slovo ''Cau''. * Můžete využít vestavěné funkce find, replace, nebo Vaše funkce z předchozí úlohy. * Pokud se ve vstupním řetězci objeví slovo ''Konec'', program skončí. V tomto řádku ale nejdříve zamění Ahoj za Cau. ==== Načítání ze souboru ==== * Načtení 1D pole ze souboru * Pole může být v souboru uloženo dvěma způsoby: * všechna čísla na jednom řádku oddělená mezerami, nebo jiným znakem * pro načtení nejdřív rozdělte řádek na řetězce podle dělicího znaku - funkce ''split()'' * pak převeďte řetězce na čísla a uložte do pole f=open('line.txt','r') line = f.readline() pole = list(map(int, line.split())) * na řádku pouze jedno číslo, počet řádek udává délku pole * otevřete soubor pro čtení - ''open''(název_souboru, "r" - read čtení) * přečtěte celý soubor po řádcích - ''readline'', nebo cyklus ''for'' * každý řádek převeďte na číslo a připojte na konec pole - funkce ''append'' pole=[] f=open('pole.txt','r') for line in f: pole.append(int(line)) * Tisk a formátování výstupu * nejjednodušší výpis jednorozměrného pole je přímo využít vestavěnou funkci print - ''print(pole)'' * pokud chcete vypsat pole na každý řádek jednu hodnotu, pak využijte cyklus ''for'' for x in pole: print(x) ==== Úkol 4 funkce nalezení maxima ==== * Napište funkci, která vrací největší hodnotu v poli a zároveň vrací index tohoto prvku * Pro pole nulové délky vrací index -1. * Pozor: je třeba předpokládat, že v poli mohou být jakékoliv hodnoty (kladné, nuly, záporné)! ==== Úkol 5 funkce nalezení druhého největšího prvku v poli ==== * Napište funkci, která vrací druhou největší hodnotu v poli a zároveň vrací index tohoto prvku * Pro pole délky méně než 2 vrací index -1. * Pozor: je třeba předpokládat, že v poli mohou být opět jakékoliv hodnoty (kladné, nuly, záporné)! ==== Polynomy ==== * Polynom $a_0 + a_1 x + a_2 x^2 + \ldots + a_n x^n$ můžeme reprezentovat polem koeficientů ''[ a_0, a_1, a_2, ... , a_n ]'' * Příklad: * polynomu $1 + x - 2x^2$ odpovídá pole ''[1, 1, -2 ]'' * polynomu $x - x^3$ odpovídá pole ''[0, 1, 0,-1 ]'' * Nulové koeficienty lze vynechat u nejvyšších mocnin, ale ne u nejnižších. * Příklad: * ''[0,1,2]'' vyjadřuje polynom $x + x^2$ * ''[0,1,2,0]'' vyjadřuje taktéž polynom $x + x^2$ * ale ''[1,2,0]'' vyjadřuje polynom $1 + 2x$ ==== Úkol 6 hezký výpis polynomu ==== * Napište funkci ''printPoly'',která vypíše polynom, přičemž mocniny bude tisknout znakem '^'. * Pokud je nějaký koeficient nulový, příslušný člen se nevypíše. * Příklad: * ''printPoly( [ 1, 1, 0, -2] )'' vytiskne ''1 + x - 2x^3'' * ''printPoly( [ -2, 0, 0, -2, 0, 0, 0] )'' vytiskne ''-2 -2x^3'' ==== Úkol 7 výpočet hodnoty polynomu ==== * Napište funkci ''polyValue'' , která pro zadaný polynom a hodnotu x vypočte jeho hodnotu v zadaném bodě $x$ * Tedy ''polyValue([1,0,2], 4)'' má hodnotu ''33'', protože $1 + 2x^2$ pro $x=4$ je 33. ===== Domácí práce ===== * Napište funkci, která pro zadaný polynom najde je maximum/minimum v zadaném intervalu $$. Řešte numericky, např. s krokem $\delta=0.1$. Nápověda: použijte funkci pro výpočet hodnoty polynomu. * Napište funkci pro výpočet první derivace polynomu: * Příklad: derivace ''[0,2,-3]'' je ''[2,-6]'' neboť derivace $2x - 3x^2$ je $2 - 6x$ ===== Domácí úkol ===== ==== Lehká varianta ==== * Napište program pro násobení dvou polynomů * **Vstup**: * Jméno souboru na příkazové řádce * Soubor obsahuje dvě řádky, na každé řádce jsou koeficienty polynomu (zadané ve stejném formátu jako v tomto cvičení), tedy polynom $a_0 + a_1 x + a_2 x^2 + \ldots + a_n x^n$ je reprezentován polem $a_0\ a_1\ a_2\ ...\ a_n$. * Koeficienty polynomu jsou celá čísla oddělená mezerou. * Vstupní polynomy mohou být různého stupně. * Je zaručeno, je že vždy zadán alespoň nultý-koeficient $a_0$. * **Výstup**: * Na standardní výstup vypište koeficienty polynomu, který vznikne vynásobením dvou vstupních polynomů. * Koeficienty jsou vypsány od nejmenšího (tj. $a_0$, $a_1$, atd.) a jsou odděleny mezerou. * Poslední vypsaný koeficient $a_i$ nesmí být roven nule pokud $i > 0$ * Tedy například: polynom $1 + 2x$ je vypsán jako '1 2', nikoliv jako '1 2 0' nebo '1 2 0 0'. * Polynom $0$ (tj. $a_0=0$) musí být vypsán jako '0'. * Polynom $0 + 3x^3$ je vypsán jako '0 0 0 3'. Výpisy typu '0 0 0 3 0 0' nebo '0 0 0 3 0 0 0 0 0' nejsou správné. * Výstupní koeficienty jsou opět celá čísla. * Program odevzdejte do úlohy HW04 pod jménem **poly.py** * Předpokládejte, že * je zaručeno, že program bude volán se jménem existujícího souboru. * je zaručeno, že vstupní soubor obsahuje správně zadané polynomy (tj. dvě řádky, na každé řádce řada celých čísel oddělená mezerou). Na každé řádce je zadáno alespoň jedno číslo. * Tipy: * Uvědomte si, jaký je stupeň výstupního polynomu v závislosti na stupni vstupních polynomů. * Může být výstupem násobení '0'? * Argument příkazové řádky předáte v terminálu (na Linuxových systémech) takto: python3 poly.py soubor.txt * Pokud používáte jiný operační systém, případně takové vývojové prostředí, kde nelze argument příkazové řádky nastavit, použijte (pro ladění) pevné jméno souboru a před odevzdáním do Bruta použijte hodnotu z sys.argv takto: filename = sys.argv[1] # tuto radku zakomentovat pro domácí ladeni filename = "soubor.txt" #tuto radku zakomentovat pro Bruta f = open(filename, "r") V následujících příkladech předpokládejte, že se program volá s argumentem, který definuje jméno vstupního souboru, např.: python3 poly.py soubor.txt Pokud ''soubor.txt'' obsahuje: 1 2 3 1 2 3 Výstup (stdout): 1 4 10 12 9 Komentář: neboť $(1 + 2x + 3x^2)(1+2x+3x^2) = 1+ 4x +10x^2 +12x^3+ 9x^4$. ---- Pokud ''soubor.txt'' obsahuje: 1 -10 Výstup (stdout): -10 ---- Pokud ''soubor.txt'' obsahuje: 36 -18 -34 11 -14 -90 -35 -84 -85 65 54 -62 67 37 1 2 -4 -81 92 24 49 -21 28 -30 -29 -88 -52 72 77 Výstup (stdout): 72 -180 -2912 4928 1890 -2811 -18 5958 -5946 -479 -7269 -15290 668 13357 -6877 10933 15164 9246 -2413 -8601 -19917 -2242 5118 -7075 -1962 7771 2921 77 ---- Pokud ''soubor.txt'' obsahuje: 0 1 69 -32 -80 -48 -29 46 43 72 -84 -81 Výstup (stdout): 0 69 -32 -80 -48 -29 46 43 72 -84 -81 ==== Těžká varianta ==== * Napište program **algebrogram.py**, který řeší jednořádkový [[https://en.wikipedia.org/wiki/Verbal_arithmetic|algebrogram]]. * Algebrogram používá pouze sčítání a odčítání bez závorek vyhodnocované zleva doprava. * Úkolem je najít takovou záměnu písmen za cifry tak, aby žádná dvě písmena neměla stejnou hodnotu a žádné číslo nezačínalo 0. * **Vstup** * Algebrogram bude zadán na jednom řádku standardního vstupu. * Algebrogram bude zadán bez mezer (tedy 'a+b=c', nikoliv 'a + b = c'). * Počet operandů na levé a pravé straně není omezen. * Písmena mohou být velká i malá. * Např.: send+more=money * **Výstup ** * Výstupem Vašeho programu bude řešení tohoto algebrogramu ve formátu dosazených cifer. * Pokud má algebrogram více řešení, vytiskněte právě jedno řešení. * Např.: 9567+1085=10652 * Pokud řešení neexistuje, bude výstupem slovo NONEXIST. * **POZOR**: Program je výpočetně náročnější, otestujte si nejdříve Váš program na svém počítači a pouze důkladně otestovaný program nahrávejte do odevzdávacího systému * **Výpočet (všech testovacích algebrogramů) je Brutovi omezen na 40s**!. ---- Vstup: SO+MANY+MORE+MEN+SEEM+TO+SAY+THAT+THEY+MAY+SOON+TRY+TO+STAY+AT+HOME+SO+AS+TO+SEE+OR+HEAR+THE+SAME+ONE+MAN+TRY+TO+MEET+THE+TEAM+ON+THE+MOON+AS+HE+HAS+AT+THE+OTHER+TEN=TESTS Výstup: 31+2764+2180+206+3002+91+374+9579+9504+274+3116+984+91+3974+79+5120+31+73+91+300+18+5078+950+3720+160+276+984+91+2009+950+9072+16+950+2116+73+50+573+79+950+19508+906=90393 ---- Vstup: AAA+BBB=EDC-BBA Výstup: 444+222=890-224 nebo 666+111=893-116 ---- Vstup: AAA-BBB=EDC-BBA Výstup: NONEXIST