Znaky - standardní typ char var Z, W: char; - znakové konstanty v apostrofech, např. a, +, (znak mezera) - proměnná zabírá 1 byte, obsahuje kód příslušného znaku - v TP (často i jinde) se používá kódová tabulka ASCII 0-31 speciální řídicí znaky 32-127 základní část znakové sady 128-255 národní abecedy resp. semigrafika - dekadické číslice souvislá řada v pořadí od 0 do 9 - velká písmena anglické abecedy souvislá řada od A do Z - malá písmena anglické abecedy souvislá řada od a do z - znakové konstanty lze zapisovat i kódem, např. #65 (totéž co A ) nebo #27 (klávesa Esc) (c) Pavel Töpfer, 2014 Programování 1-7 1
- lze používat v procedurách read, write např. read(z); write( Z ); POZOR v příkladu výše rozlišovat Z a Z! - do proměnné lze dosazovat, např. W:=? ; Z:=W; - na typu char je definováno uspořádání (podle kódů), je možné používat relační operátory =, <, >, <=, >=, <> if (Z>= A ) and (Z<= Z ) then {hodnotou proměnné Z je velké písmeno anglické abecedy} while Z <> W do {dokud mají proměnné Z a W různou hodnotu} (c) Pavel Töpfer, 2014 Programování 1-7 2
Standardní funkce var Z, Z1: char; B: byte; B := ord(z); Z := chr(b); vrací kód znaku Z v ASCII-tabulce (ordinální hodnotu) k zadanému ASCII-kódu vrací příslušný znak - funkce navzájem inverzní tedy chr(ord(z)) = Z - z hlediska syntaxe jazyka jde o přetypování - v kódu se nic neděje (znak je stejně reprezentován svým kódem) Použití: B:=ord(Z) ord( 0 ); cifra její hodnota Z:=chr(B+ord( 0 )); hodnota 0..9 cifra Z1 := UpCase(Z) malá písmena anglické abecedy změní na velká, ostatní znaky ponechá beze změny Použití: místo delšího if UpCase(Z) = A then if (Z= A ) or (Z= a ) then (c) Pavel Töpfer, 2014 Programování 1-7 3
Příklad: vstup čísla po znacích - co přibližně dělá procedura read - algoritmus: Hornerovo schéma var Zn: char; {čtené znaky} Hodn: integer; {číselná hodnota} Hodn:=0; read(zn); while (Zn>= 0 ) and (Zn<= 9 ) do Hodn := Hodn*10 + ord(zn) ord( 0 ); read(zn) end; {výsledná hodnota je v proměnné Hodn} Pro jednoduchost předpokládáme korektní vstup, bez vedoucích mezer. (c) Pavel Töpfer, 2014 Programování 1-7 4
Znakové řetězce - standardní typ string type JmenoTypu = string [N]; N celočíselná konstanta udávající maximální délku stringu N je nejvýše rovno 255 pokud N neuvedeme, implicitní hodnota je 255 Příklad: type JmenoMesice = string[8]; var Mesic: JmenoMesice; {proměnná pro řetězce max. 8 znaků} S: string; {proměnná pro řetězce max. 255 znaků} Reprezentace proměnné: - jednorozměrné pole znaků indexované od 1 do N - vlastní evidence aktuální délky uloženého řetězce (v bytu s indexem 0 pozor při manipulaci, formálně je typu char) (c) Pavel Töpfer, 2014 Programování 1-7 5
Konstanty: duben řetězec délky 5 znaků? řetězec délky 1 znak (jako char) prázdný řetězec (žádný znak) Operace se stringy: - do proměnné lze dosazovat, např. Mesic := duben ; nastaví se tím aktuální délka (zde na 5) - jediný operátor + znamená zřetězení, např. po provedení S := 12. + Mesic; bude mít proměnná S hodnotu 12. duben a aktuální délku 9 - lze používat v procedurách read, write read(s); - načte tolik znaků, kolik je maximální délka S, nejvýše však do konce řádku na vstupu write(s); - vypíše tolik znaků, kolik je aktuální délka S Doporučení: Při čtení používat raději readln(s) přijdeme sice případně o znaky, které se nevešly do maximální délky S, zato při následujícím čtení budeme číst od začátku dalšího řádku. Jinak při čtení dalšího stringu ze vstupu načteme prázdný řetězec! (c) Pavel Töpfer, 2014 Programování 1-7 6
Standardní procedury a funkce se znakovými řetězci Length(S) aktuální délka řetězce Concat(S1, S2,, Sn) spojení řetězců za sebe totéž se snáze zapíše operátorem + : S1 + S2 + + Sn Copy(S, Index, Pocet) vykopírování podřetězce dané délky počínaje od daného indexu Delete(S, Index, Pocet) v řetězci S zruší podřetězec dané délky počínaje od daného indexu Insert(Co, Kam, Index) do řetězce Kam vloží Co na pozici daného indexu Pos(Co, Kde) pozice prvního výskytu podřetězce Co v řetězci Kde (0 když tam není obsažen) (c) Pavel Töpfer, 2014 Programování 1-7 7
Indexování: S[i] = i-tý znak řetězce S, je typu char S[2] := 5 ; for I:=1 to length(s) do if S[I] =? then S[I] :=! ; {v řetězci S nahradí všechny otazníky vykřičníkem} POZOR při indexování stringu změny neovlivňují aktuální délku: S:= ABC ; {aktuální délka S je 3} for I:= 1 to 10 do S[I]:= Z ; {do S se vloží 10 znaků, ale aktuální délka S zůstává nastavena na 3} write(s); {vypíše ZZZ } Uspořádání stringů - lexikografické, indukované uspořádáním na typu char 4 < Z < f < fa < fb < g < č < á - je možné používat relační operátory =, <, >, <=, >=, <> (c) Pavel Töpfer, 2014 Programování 1-7 8
Příklad: načtení dlouhého čísla (kladné celé, max. 100 cifer) type Cislo = array [1..100] of byte; var A: Cislo; {A[1] cifra v řádu jednotek} PA: byte; {počet cifer} S: string[100]; I: integer; readln(s); PA := 0; for I:=length(S) downto 1 do inc(pa); A[PA] := ord(s[i])-ord( 0 ) end; (c) Pavel Töpfer, 2014 Programování 1-7 9
Číselné soustavy - převod z dvojkové soustavy na číselnou hodnotu - algoritmus: Hornerovo schéma 110010 1.2 5 + 1.2 4 + 0.2 3 + 0.2 2 + 1.2 1 + 0.2 0 = = ((((1.2 + 1).2 + 0).2 + 0).2 + 1).2 + 0 = 50 - převod z šestnáctkové soustavy na číselnou hodnotu A1F A.16 2 + 1.16 1 + F.16 0 = = 10.16 2 + 1.16 1 + 15.16 0 = = (10.16 + 1).16 + 15 = 2591 (c) Pavel Töpfer, 2014 Programování 1-7 10
program Bin_Dec; {převod čísla z dvojkové soustavy - Hornerovo schéma} var S: string[15]; {dvojkový zápis čísla} N: integer; {jeho hodnota} I: integer; read(s); N:=0; for I:= 1 to length(s) do N:=N*2 + ord(s[i])-ord('0'); writeln('hodnota: ', N) end. (c) Pavel Töpfer, 2014 Programování 1-7 11
program Hex_Dec; {převod čísla z šestnáctkové soustavy - Hornerovo schéma} var S: string[15]; {šestnáctkový zápis čísla} N: integer; {jeho hodnota} I: integer; read(s); N:=0; for I:= 1 to length(s) do if (S[I]>='0') and (S[I]<='9') then N:=N*16 + ord(s[i])-ord('0') else N:=N*16 + ord(s[i])-ord('a') + 10; end; writeln('hodnota: ', N) end. (c) Pavel Töpfer, 2014 Programování 1-7 12
110010 1.2 5 + 1.2 4 + 0.2 3 + 0.2 2 + 1.2 1 + 0.2 0 = = ((((1.2 + 1).2 + 0).2 + 0).2 + 1).2 + 0 = 50 - převod číselné hodnoty do dvojkové soustavy - algoritmus: Hornerovo schéma využité v opačném směru posloupnost zbytků při celočíselném dělení dvěma tvoří odzadu dvojkový zápis čísla připojování dvojkových cifer do stringu zleva 50 : 2 = 25, zb. 0 25 : 2 = 12, zb. 1 12 : 2 = 6, zb. 0 6 : 2 = 3, zb. 0 3 : 2 = 1, zb. 1 1 : 2 = 0, zb. 1 (c) Pavel Töpfer, 2014 Programování 1-7 13
program Dec_Bin; {převod čísla do dvojkové soustavy - obrácené Hornerovo schéma} var S: string[15]; {dvojkový zápis čísla} N: integer; {jeho hodnota} read(n); S:=''; {prázdný řetězec} while N > 0 do if odd(n) then S:='1'+S else S:='0'+S; N:=N div 2 end; writeln('dvojkový zápis čísla: ', S) end. (c) Pavel Töpfer, 2014 Programování 1-7 14
program Dec_Hex; {převod čísla do šestnáctkové soustavy - obrácené Hornerovo schéma} var S: string[15]; {šestnáctkový zápis čísla} N: integer; {jeho hodnota} Z: integer; read(n); S:=''; {prázdný řetězec} while N > 0 do Z:=N mod 16; if (Z <= 9) then S:= chr(z + ord('0')) + S else S:= chr(z 10 + ord('a')) + S; N:=N div 16; end; writeln('šestnáctkový zápis čísla: ', S) end. (c) Pavel Töpfer, 2014 Programování 1-7 15
Konverzní procedury Str(V, S) - konverze číselná hodnota V string S - V může být výraz typu integer nebo real - součástí V může být formátování V:n resp. V:n:m jako u write - volání Str se implicitně provádí v proceduře write (zápis čísla) Val(S, V, ErrCode) - konverze string S číselná hodnota V - V může být proměnná typu integer nebo real - ErrCode=0 převod se povedl bez chyby - ErrCode>0 pozice výskytu chyby (index v S) - volání Val se implicitně provádí v proceduře read (čtení čísla) (c) Pavel Töpfer, 2014 Programování 1-7 16