Linux E X P R E S

Facebook

Programovanie v jazyku C++: Pointery ukazujúce na funkcie

cplusplus.png

Vedeli ste, že pointery môžu ukazovať nielen na rôzne typy premenných, ale aj na funkcie? Ukážeme si, ako vytvoriť pointer, ktorý ukazuje na zvolenú funkciu.


Definujeme pointery ukazujúce na funkcie

Už vieme, že pointer je premenná, ktorá uchováva adresu inej premennej. Pointer môže ukazovať nielen na umiestnenie inej premennej, ale aj na umiestnenie samotnej funkcie! Aby sme si to ukázali, na začiatok si implementujeme jednoduchý program. Tento program nám bude slúžiť ako odrazový mostík vo vysvetľovaní.

#include <iostream>

#include <ctime>

#include <cstdlib>

using namespace std;

 

void vypis(int nahodneCislo)

{

    cout << "Z intervalu 1-100 bolo vylosovane cislo: " << nahodneCislo << "\n";

}

 

int main()

{

    srand(time(0));

    int nahodneCislo = rand() % 100 + 1;

    vypis(nahodneCislo);

    return 0;

}

Výsledok programu:

Z intervalu 1-100 bolo vylosovane cislo: 33

Vytvorili sme jednoduchý program, ktorý vylosuje náhodne číslo v intervale od 1 do 100. Nič komplikované. Skúsme však definovať pointer, ktorý bude ukazovať na funkciu vypis().

#include <iostream>

using namespace std;

 

void vypis()

{

    cout << "Ahoj mily pouzivatel. Som ti uplne k dispozicii :)";

}

 

int main()

{

    void (*pointerVypis)() = vypis;

    pointerVypis();

    return 0;

}

Výsledok programu:

Ahoj mily pouzivatel. Som ti uplne k dispozicii :)

Takže čo sa zmenilo? Museli sme pridať jeden riadok kódu, aby sme definovali pointer, ktorý bude ukazovať na našu definovanú funkciu vypis(). Celé znenie aj už s priradením adresy funkcie do prázdneho pointeru vyzerá takto: void (*pointerVypis)() = vypis;. Do zátvorky sme dali deklaračný znak pointeru * a meno pointeru. Pravidla priradenia adresy funkcie pre pointer je rovnaká ako u premenných.

Teraz sa vráťme k prvému príkladu a upravme ho tak, aby pointer ukazoval na funkciu s jedným parametrom.

#include <iostream>

#include <ctime>

#include <cstdlib>

using namespace std;

 

void vypis(int nahodneCislo)

{

    cout << "Z intervalu 1-100 bolo vylosovane cislo: " << nahodneCislo << "\n";

}

 

int main()

{

    srand(time(0));

    int nahodneCislo = rand() % 100 + 1;

    void (*los)(int) = vypis;

    los(nahodneCislo);

    return 0;

}

Výsledok je samozrejme rovnaký, len vylosovaná hodnota je iná. Všimnite si, že sme pridali do zátvorky int, viď. void (*los)(int) = vypis;.

Teraz skúsme zmeniť funkciu vypis() tak, aby vracala návratovú hodnotu typu int. Uspôsobíme aj tvorbu pointeru tak, aby ukazoval na funkciu s návratovou hodnotou int.

#include <ctime>

#include <cstdlib>

using namespace std;

 

int vypis(int nahodneCislo)

{

    nahodneCislo = rand() % 100 + 1;

    return nahodneCislo;

}

 

int main()

{

    srand(time(0));

    int nahodneCislo = 0;

    int (*los)(int) = vypis;

    nahodneCislo = los(nahodneCislo);

    cout << "Z intervalu 1-100 bolo vylosovane cislo: " << nahodneCislo << "\n";

    return 0;

}

Oproti predchádzajúcemu príkladu, sme upravili tvorbu pointeru aj zmenili funkciu výpis() tak, aby vrátila celočíselné hodnoty, čiže typu int.

Zvládli sme základy tvorby pointerov, ktoré odkazujú na funkcie. Zatiaľ to však vyzerá, že je to viacmenej zbytočné. Predsa, všetky uvedené príklady sa dajú použiť aj bez pointerov na funkcie a dokonca ušetríme minimálne jeden riadok kódu. Skúsme sa ale pozrieť na príklad, v ktorom potencionálne pointer ukazujúci na funkciu môže byť užitočný.

#include <iostream>

#include <ctime>

#include <cstdlib>

using namespace std;

 

void chybovaHlaska()

{

    cout << "Nulou sa nedeli! Program predcasne konci!\n";

    exit(0);

}

 

int scitanie(int nahodneCislo1, int nahodneCislo2)

{

    int vysledok = nahodneCislo1 + nahodneCislo2;

    return vysledok;

}

 

int odcitanie(int nahodneCislo1, int nahodneCislo2)

{

    int vysledok = nahodneCislo1 - nahodneCislo2;

    return vysledok;

}

 

int nasobenie(int nahodneCislo1, int nahodneCislo2)

{

    int vysledok = nahodneCislo1 * nahodneCislo2;

    return vysledok;

}

 

int delenie(int nahodneCislo1, int nahodneCislo2)

{

    int vysledok = 0;

    if(nahodneCislo2 != 0)

        vysledok = nahodneCislo1 / nahodneCislo2;

    else chybovaHlaska();

    return vysledok;

}

 

int main()

{

    srand(time(0));

    int nahodneCislo1 = rand() % 100;

    int nahodneCislo2 = rand() % 100;

    int volba = 0;

    int (*mat_operation)(int,int);

    cout << "Zvol operaciu:\n" << "1 - scitanie\n" << "2 - odcitanie\n" << "3 - nasobenie\n" << "4 - delenie\n";

    cout << "Tvoja volba je: ";

    cin >> volba;

    if(volba == 1)

        mat_operation = scitanie;

    else if (volba == 2)

        mat_operation = odcitanie;

    else if (volba == 3)

        mat_operation = nasobenie;

    else if (volba == 4)

        mat_operation = delenie;

    else

    {

        cout << "Neplatna volba, program konci!\n";

        return 0;

    }

 

    cout << "Vysledok vasej zvolenej operacie medzi dvoma nahodnymi cislami "<<nahodneCislo1<< " a "<<nahodneCislo2 << " je: " << mat_operation(nahodneCislo1, nahodneCislo2) << "\n";

    return 0;

}

Výsledkom programu je:

Zvol operaciu:

1 - scitanie

2 - odcitanie

3 - nasobenie

4 - delenie

Tvoja volba je: 2

Vysledok vasej zvolenej operacie medzi dvoma nahodnymi cislami 69 a 46 je: 23

Princípom programu je, že užívateľ si vyberie, aká matematická operácia sa vykoná nad dvoma číslami. Po vybratí matematickej operácie sa priradí pointeru tá funkcia, ktorú vybral používateľ. Čiže ak vybral sčítanie, tak vyberie funkciu scitanie(). Takáto implementácia ukazuje smer, ako môžete využiť pointery ukazujúce na funkcie.

Námet na tento článok poslúžili tieto zdroje:

7.8 — Function Pointers, learncpp.com, dostupné online

Function Pointer in C, geeksforgeeks.org, dostupné online

Diskuze (7) Nahoru