Funkce a pole
Argumentem může být i pole. Funkce, která dostane pole, ho může projít cyklem a vrátit třeba součet jeho prvků:
#include <stdio.h>
int soucet(int cisla[], int pocet) {
int celkem = 0;
for (int i = 0; i < pocet; i++) {
celkem += cisla[i];
}
return celkem;
}
int main(void) {
int body[] = {8, 5, 10};
int goly[] = {2, 0, 1, 3, 1};
printf("%d\n", soucet(body, 3));
printf("%d\n", soucet(goly, 5));
return 0;
}Tento program vypíše:
23
7Parametr int cisla[] je pole hodnot typu int. Hranaté závorky jsou prázdné, protože funkce může dostat pole jakékoli velikosti. Ve volání napíšete jen název pole, bez závorek: soucet(body, 3). Se závorkami, soucet(body[], 3), se program nepřeloží: error: expected expression (očekáván výraz).
Proč je tu druhý parametr, pocet? Funkce neví, kolik má pole prvků, a tak jí to musíte říct. Nezkoušejte uvnitř funkce sizeof(cisla) / sizeof(cisla[0]): tam cisla ve skutečnosti není celé pole (co to je, uvidíte v příští lekci, o ukazatelích), a tak sizeof jeho prvky nespočítá. Překladač na to jen upozorní varováním, které tento web nezobrazuje, a počet vyjde špatně (tady 1, takže funkce by sečetla jen první prvek). Počet zjistěte tam, kde pole vzniklo, tedy v main, a funkci ho předejte. A dejte pozor, aby počet seděl: s větším počtem by funkce četla za koncem pole, a to je chyba, kterou znáte z lekce o polích.
Všimněte si, kde je return: až za }, která ukončuje cyklus, tedy když jsou sečtené všechny prvky. Častou chybou je dát ho o řádek výš, dovnitř cyklu. Pak by ukončil celou funkci hned při prvním průchodu cyklem. Tady se takový program ani nepřeloží: non-void function does not return a value in all control paths. S počtem 0 by se totiž cyklus vůbec neprovedl a funkce by došla na konec bez return.
Mezi poli a čísly je jeden velký rozdíl. Parametr s číslem dostane kopii, jak jste viděli v minulém cvičení. Pole se ale nekopíruje: funkce dostane přímo to pole, které jí volající předal. Když tedy funkce změní jeho prvky, změny v poli v main zůstanou:
#include <stdio.h>
void pricti_vsem(int cisla[], int pocet, int kolik) {
for (int i = 0; i < pocet; i++) {
cisla[i] += kolik;
}
}
int main(void) {
int body[] = {5, 8, 7};
pricti_vsem(body, 3, 10);
for (int i = 0; i < 3; i++) {
printf("%d\n", body[i]);
}
return 0;
}Tento program vypíše:
15
18
17Funkce přičetla 10 ke každému prvku pole body v main. Proč se pole chovají takhle, zjistíte v příští lekci, o ukazatelích. Zatím si zapamatujte, že funkce může změnit prvky pole, které jí předáte.
Jak psát:
Pokyny
Program se nepřeloží, protože funkce prumer zatím neexistuje (přečtěte si první chybu). Napište ji místo komentáře: bude mít dva parametry, pole cisla typu int a jeho pocet typu int, a vrátí průměr prvků jako double: jejich součet vydělený počtem. Pozor na celočíselné dělení: součet ukládejte do proměnné typu double. Program pak vypíše průměrné teploty dvou týdnů, 20.80 a 12.75.
V prvním týdnu ukazoval teploměr každou teplotu o 1 stupeň nižší, než skutečně byla. Pod funkci prumer napište funkci pricti_vsem se třemi parametry: pole cisla typu int, jeho pocet a kolik (oba typu int). Funkce přičte kolik ke každému prvku pole a nic nevrací. Na konci main, před return 0;, zavolejte pricti_vsem(tyden1, 5, 1) a pak stejně jako nahoře znovu vypište průměr tyden1. Program vypíše 21.80: funkce změnila pole v main.
Začněte programovat zdarma
9/12