Pointery II. Jan Hnilica Počítačové modelování 17

Podobné dokumenty
IUJCE 07/08 Přednáška č. 4. v paměti neexistuje. v paměti existuje

Dynamická vícerozměrná pole. Základy programování 2 Tomáš Kühr

Správné vytvoření a otevření textového souboru pro čtení a zápis představuje

Vícerozměrná pole. Úvod do programování 2 Tomáš Kühr

Strukturu lze funkci předat: (pole[i])+j. switch(výraz) velikost ukazatele

Střední škola pedagogická, hotelnictví a služeb, Litoměříce, příspěvková organizace

Př. další použití pointerů

Pole a Funkce. Úvod do programování 1 Tomáš Kühr

IUJCE 07/08 Přednáška č. 6

11a Dynamické dvourozměrné pole (obdobně vícerozměrné)

Pole stručný úvod do začátku, podrobně později - zatím statická pole (ne dynamicky) - číslují se od 0

Ukazatele a pole. Chceme-li vyplnit celé pole nulami, použijeme prázdný inicializátor: 207 Čárka na konci seznamu inicializátorů

Pole a kolekce. v C#, Javě a C++

Lineární spojový seznam (úvod do dynamických datových struktur)

Strukturované typy a ukazatele. Úvod do programování 1 Tomáš Kühr

Práce s polem a pamětí

Algoritmizace a programování

6. lekce Úvod do jazyka C knihovny datové typy, definice proměnných základní struktura programu a jeho editace Miroslav Jílek

Úvod do programování - Java. Cvičení č.4

POČÍTAČE A PROGRAMOVÁNÍ

2 Datové typy v jazyce C

- dělají se také pomocí #define - podobné (použitím) funkcím - předpřipravená jsou např. v ctype.h. - jak na vlastní makro:

Ukazatele, dynamická alokace

8. lekce Úvod do jazyka C 3. část Základní příkazy jazyka C Miroslav Jílek

Základy C++ I. Jan Hnilica Počítačové modelování 18

C++ přetěžování funkcí a operátorů. Jan Hnilica Počítačové modelování 19

Struktura programu v době běhu

Dynamická alokace paměti

Programování v C++, 2. cvičení

Ukazatele #2, dynamická alokace paměti

Programovací jazyk Pascal

ZPRO v "C" Ing. Vít Hanousek. verze 0.3

EVROPSKÝ SOCIÁLNÍ FOND. Úvod do PHP PRAHA & EU INVESTUJEME DO VAŠÍ BUDOUCNOSTI

Aplikace Embedded systémů v Mechatronice. Michal Bastl A2/713a

for (i = 0, j = 5; i < 10; i++) { // tělo cyklu }

Základní datové struktury

IAJCE Přednáška č. 8. double tprumer = (t1 + t2 + t3 + t4 + t5 + t6 + t7) / 7; Console.Write("\nPrumerna teplota je {0}", tprumer);

Programování v jazyce C pro chemiky (C2160) 3. Příkaz switch, příkaz cyklu for, operátory ++ a --, pole

přetížení operátorů (o)

for (int i = 0; i < sizeof(hodnoty) / sizeof(int); i++) { cout<<hodonoty[i]<< endl; } cin.get(); return 0; }

PROGRAMOVÁNÍ V JAZYCE C V PŘÍKLADECH 11 Dynamické datové struktury 11.1 Spojové struktury Příklad PROG_

Algoritmizace a programování

Základy programování (IZP)

1. lekce. do souboru main.c uložíme následující kód a pomocí F9 ho zkompilujeme a spustíme:

Funkce, intuitivní chápání složitosti

7 Formátovaný výstup, třídy, objekty, pole, chyby v programech

BI-PA1 Programování a algoritmizace 1, ZS Katedra teoretické informatiky

Martin Flusser. Faculty of Nuclear Sciences and Physical Engineering Czech Technical University in Prague. December 7, 2016

int t1, t2, t3, t4, t5, t6, t7, prumer; t1=sys.readint();... t7=sys.readint(); prume pru r = r = ( 1+t 1+t t3+ t3+ t4 t5+ t5+ +t7 +t7 )/ ;

Mělká a hluboká kopie

Operační systémy. Cvičení 4: Programování v C pod Unixem

Střední škola pedagogická, hotelnictví a služeb, Litoměříce, příspěvková organizace

1. lekce. do souboru main.c uložíme následující kód a pomocí F9 ho zkompilujeme a spustíme:

Jazyk C práce se soubory. Jan Hnilica Počítačové modelování 16

Algoritmizace a programování

Čtvrtek 8. prosince. Pascal - opakování základů. Struktura programu:

9. lekce Úvod do jazyka C 4. část Funkce, rekurze Editace, kompilace, spuštění Miroslav Jílek

Více o konstruktorech a destruktorech

Logické operace. Datový typ bool. Relační operátory. Logické operátory. IAJCE Přednáška č. 3. může nabýt hodnot: o true o false

4. Typ ukazatel, strukturované datové typy

Úvod do jazyka C. Ing. Jan Fikejz (KST, FEI) 28. prosince Fakulta elektrotechniky a informatiky Katedra softwarových technologií

Funkce pokročilé možnosti. Úvod do programování 2 Tomáš Kühr

Sada 1 - Základy programování

Stromy. Jan Hnilica Počítačové modelování 14

Paměť počítače. alg2 1

Obsah. Předmluva 13 Zpětná vazba od čtenářů 14 Zdrojové kódy ke knize 15 Errata 15

Základy programování (IZP)

1. D Y N A M I C K É DAT O V É STRUKTUR Y

PROMĚNNÉ, KONSTANTY A DATOVÉ TYPY TEORIE DATUM VYTVOŘENÍ: KLÍČOVÁ AKTIVITA: 02 PROGRAMOVÁNÍ 2. ROČNÍK (PRG2) HODINOVÁ DOTACE: 1

DUM 07 téma: Proměnné, konstanty a pohyb po buňkách ve VBA

6 Příkazy řízení toku

Práce s binárními soubory. Základy programování 2 Tomáš Kühr

Základní způsoby: -Statické (přidělění paměti v čase překladu) -Dynamické (přiděleno v run time) v zásobníku na haldě

int ii char [16] double dd název adresa / proměnná N = nevyužito xxx xxx xxx N xxx xxx N xxx N

Pokročilé programování v jazyce C pro chemiky (C3220) Operátory new a delete, virtuální metody

Pascal. Katedra aplikované kybernetiky. Ing. Miroslav Vavroušek. Verze 7

Příklad : String txt1 = new String( Ahoj vsichni! ); //vytvoří instanci třídy String a přiřadí ji vnitřní hodnotu Ahoj vsichni!

Odvozené a strukturované typy dat

Obsah přednášky. Příkaz for neúplný. Příkaz for příklady. Cyklus for each (enhanced for loop) Příkaz for příklady

Výrazy a operátory. Operátory Unární - unární a unární + Např.: a +b

Maturitní otázky z předmětu PROGRAMOVÁNÍ

Základy programování (IZP)

Ukazatel (Pointer) jako datový typ - proměnné jsou umístěny v paměti na určitém místě (adrese) a zabírají určitý prostor (počet bytů), který je daný

Základní způsoby: -Statické (přidělění paměti v čase překladu) -Dynamické (přiděleno v run time) v zásobníku na haldě

MAXScript výukový kurz

Bitové operátory a bitová pole. Úvod do programování 2 Tomáš Kühr

Množina čísel int stl-set-int.cpp

Operátory, výrazy. Tomáš Pitner, upravil Marek Šabo

5 Přehled operátorů, příkazy, přetypování

dovolují dělení velkých úloh na menší = dekompozice

Jazyk C Program v jazyku C má následující strukturu: konstanty nebo proměnné musí Jednoduché datové typy: Strukturované datové typy Výrazy operátory

Vyučovací hodina. 1vyučovací hodina: 2vyučovací hodiny: Opakování z minulé hodiny. Procvičení nové látky

KTE / ZPE Informační technologie

Úvod do programování. Lekce 1

2) Napište algoritmus pro vložení položky na konec dvousměrného seznamu. 3) Napište algoritmus pro vyhledání položky v binárním stromu.

Programování v jazyce C a C++

cyklus s daným počtem opakování cyklus s podmínkou na začátku (cyklus bez udání počtu opakování)

Základy programování (IZP)

Spojová implementace lineárních datových struktur

Práce s pamětí a předávání parametrů. Úvod do programování 1

Transkript:

Pointery II 1

Pointery a pole Dosavadní způsob práce s poli zahrnoval: definici pole jakožto kolekce proměnných (prvků) jednoho typu, umístěných v paměti za sebou int pole[10]; práci s jednotlivými prvky pole pomocí indexu v hranatých závorkách for (int i = 0; i < 10; i++) pole[i] = i + 1; Výše uvedený způsob často postačuje, ale jazyk C nabízí rozšíření možností práce s poli a její zefektivnění pomocí úzkého vztahu polí a pointerů. Ten vyplývá z toho, že název pole je ve skutečnosti pointerem na první prvek pole 2

Statické pole int pole[6]; proměnná pole je pointer na int obsahuje adresu počátku bloku paměti, kde je za sebou uloženo 6 proměnných typu int tímto způsobem vznikne tzv. statické pole, uložené na zásobníku (má tedy lokální obor platnosti odpovídající funkci či bloku, ve kterém bylo definováno, po jejím opuštění zanikne) u statického pole je název pole konstantní pointer (adresa v něm uložená se nedá měnit) předpokládejme, že int zabere 4 bajty paměti, pak definice int pole[6]; vytvoří pole[0] pole[1] pole[2] pole[3] pole[4] pole[5] pole: adresa (např.): 100 104 108 112 116 120 samotná proměnná pole je pointer na int, obsahující adresu 100 můžeme napsat int * pint = pole;, pak pint ukazuje do stejného místa paměti jako pole (tedy na první prvek pole) 3

Dynamické pole int * pole = (int*) malloc(6 * sizeof(int)); proměnná pole je opět pointer na int, obsahující adresu počátku bloku paměti, kde je za sebou uloženo 6 proměnných typu int tímto způsobem vznikne tzv. dynamické pole, uložené na haldě, které zanikne až uvolněním paměti příkazem free(pole);, na což nesmíme zapomínat název pole není konstantní pointer (pokud ho tedy sami jako konstantní nedefinujeme) s dynamickým polem lze pracovat stejně jako se statickým, tzn. funguje tu indexování pole[2] = 7; 7 dynamická a statická pole se liší se umístěním v paměti a životností, ale práce s nimi je stejná Funkce přebírající pole jako parametr může být deklarována takto nebo takto int SumaPrvku(int pole[], int pocetprvku); int SumaPrvku(int * pole, int pocetprvku); Obě funkce mohou uvnitř pracovat naprosto stejně. 4

Pointerová aritmetika s pointery je možné provádět aritmetické operace, které využijeme hlavně při práci s poli smysl mají 4 operace: 1) součet pointeru a celého čísla (pointer + n) výsledkem je pointer, ukazující na n-tý prvek za prvkem, na který ukazuje původní pointer k adrese dané pointerem se tedy nepřičítá n, ale n * velikost typu, na který pointer ukazuje příklad: proměnná int a zabírá 4 bajty paměti, pointer pa ukazuje na tuto proměnnou: int a 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 pa pa + 1 pa + 2 pa + 3 pa + 1... k hodnotě pa se přičte hodnota 4 (velikost typu int) pa + 1 neukazuje o jeden bajt dál, ale o jeden int dál pint = pint + 1; // poskočení o 1 prvek dozadu pint++; // totéž 5

2) rozdíl pointeru a celého čísla (pointer - n) opačná operace, výsledkem je pointer, ukazující na n-tý prvek před prvkem, na který ukazuje původní pointer posun zpět o n prvků, tedy o n * sizeof(*pointer) bajtů pint--; // posun o jeden prvek doleva 3) porovnávání pointerů lze použít relační operátory <, <=, >, >=, ==,!= if (p1 < p2)... test, jestli p1 ukazuje před p2 (tzn. jestli adresa v p1 je menší než v p2) if (p1 == p2)... test, jestli p1 a p2 ukazují na stejné místo paměti smysl má pouze porovnávat pointery na stejný datový typ 3) odečítání pointerů pkonec pzacatek... výraz vrací počet prvků mezi pointery (ne počet bajtů) smysl má pouze, pokud pointery ukazují na stejný datový typ a zároveň ukazují do stejného pole pzacatek pkonec pkonec pzacatek == 4 6

Využití pointerové aritmetiky při práci s poli pomocí indexu pomocí pointerů přístup k prvku pole pole[i] *(pole + i) adresa prvku pole &pole[i] pole + i průchod polem (spojený např. s vynulováním prvků) int pole[10]; for (int * p = pole; p < pole + 10; p++) *p = 0; kopírování obsahu pole A do pole B int * p1 = polea; int * p2 = poleb; for (int i = 0; i < pocetprvku; i++) { *p2 = *p1; p1++; p2++; } pozn. cyklus lze napsat i úsporněji: for (int i = 0; i < pocetprvku; i++) *p2++ = *p1++; 7

Využití pointerové aritmetiky při práci s poli zvětšení dynamického pole máme dynamické pole 100 prvků, ketré je zaplněné a pro přidávání dalších hodnot mu musíme navýšit kapacitu (např. ji zdvojnásobíme): int * pole = (int*) malloc(100 * sizeof(int));... // pole je plné, zvýšíme mu kapacitu: int * novepole = (int*) malloc(200 * sizeof(int)); int *p1 = pole, *p2 = novepole; for (int i = 0; i < 100; i++) *p2++ = *p1++; free(pole); pole = novepole; // a nikdo nic nepozná... 8

Využití pointerové aritmetiky při práci s poli Motivace - proč používat pointerovou aritmetiku? práce s polem pomocí pointerů je efektivnější než pomocí indexů (ačkoliv výsledek je stejný) příklad: máme pole int pole[1000]; a chceme jeho prvky vynulovat: A) pomocí indexů: for (int i = 0; i < 1000; i++) pole[i] = 0; v každé iteraci se pro přístup k prvku pole 1. spočítá (i * velikost prvku pole) 2. výsledek se přičte k bázové adrese pole B) pomocí pointerů: for (int * p = pole; p < pole + 1000; p++) *p = 0; v každé iteraci se pouze přičte k pointeru p konstanta Ovšem platí, že práci s polem pomocí indexů a pointerů lze libovolně kombinovat či používat jen jeden způsob, a to jak u statických tak i u dynamických polí. 9

Vícerozměrná pole Způsob uložení vícerozměrných polí v paměti např. 2D pole int pole[3][4] je pole o 3 řádcích a 4 sloupcích každý řádek je uložen zvlášť jako jednorozměrné pole (délky 4) jednorozměrné pole je uloženo jako pointer na první prvek, takže: pole[3][4] je pole 3 pointerů, každý z nich ukazuje na 1D pole délky 4 pole[0] pole[1] pole[2] Proměnná Význam Aritmetika pole pointer na 2D pole (typ int**) pole + 1 posun na další řádek pole[i] pointer na 1D pole (typ int*) pole[i] + 1 posun na další prvek pole[i] pole[i][j] jednoduchá proměnná (typ int) 10

Dvourozměrné dynamické pole Způsoby vytvoření dvourozměrného pole na haldě jako pole pointerů int * pole[3]; for (int i = 0; i < 3; i++) pole[i] = (int*)malloc(4 * sizeof(int)); jako pointer na pointer int ** pole = (int**)malloc(3 * sizeof(int*)); for (int i = 0; i < 3; i++) pole[i] = (int*)malloc(4 * sizeof(int)); Jaký je rozdíl mezi těmto dvěma poli??? pozn. cyklus pro vytvoření řádek je u obou způsobů stejný u obou polí lze využívat jak pointerovou aritmetiku, tak indexování (stejně jako u statického pole) Smazání pole (uvolnění paměti) for (int i = 0; i < 3; i++) free(pole[i]); free(pole); 11

Dvourozměrné dynamické pole dynamické pole může být zubaté (každá řádka jinak dlouhá) char * pole[4]; pole[0] = "ahoj"; pole[1] = "baf"; pole[2] = "kebule"; pole[3] = "cejn"; pole[0] pole[1] pole[2] pole[3] a h o j \0 b a f \0 k e b u l e \0 c e j n \0 12

Pointer na funkci kód funkce je uložen v paměti stejně jako data, může na něj být odkazováno paměťovou adresou adresu kódu je dostupná prostřednictvím názvu funkce, který funguje jako pointer deklarace funkce, vracející double double Funkce(int a); pointer na funkci, vracející double (závorky kolem názvu pointeru jsou nutné, stejně tak jako závorky na konci definice) double (*pfunkce)(); dosazení adresy funkce do pointeru pfunkce = Funkce; volání funkce pomocí pointeru double vysledek = pfunkce(10.3); 13

Pointer na funkci při psaní uživatelské nabídky může být výhodné vytvořit pole pointerů na funkci př. vytvoření pole 3 pointerů na funkce, vracející hodnotu double: double (*funkce[3])(); // pole 3 pointerů na funkce double (*funkce[3])(); // funkce prumer, rozptyl a median byly deklarovány dřív // všechny přebírají pole čísel a počet prvků pole funkce[0] = prumer; funkce[1] = rozptyl; funkce[2] = median; int volba; printf("co chcete spocitat?\n"); printf("<0> prumer\n"); printf("<1> rozptyl\n"); printf("<2> median\n"); printf("vase volba: "); scanf("%i", &volba); double vysledek = funkce[volba](pole, n); // výpočet výsledku 14