C++ Tutorijali

Teme vezane za console/GUI programiranje u C/C++ jeziku
11 post(ov)a • Stranica: 2/2.1, 2

Re: C++ Tutorijali

PostPostao/la gagiD » 27 srp 2014, 15:43

slika


OPĆENITO O FUNKCIJAMA:

U programiranju često imamo potrebu da neki kod iskoristimo vise puta. Takoder vrlo korisno pravilo u programirnju je DRY - "Don't repeat yourself", što znači da isti kod nikada ne trebamo pisati dva ili više puta. To dosta utiče na produktivnost. U tu svrhu koristimo funkcije. Kada želimo neki kod napisati jednom i iskoristiti više puta.

Opšti oblik funkcije:
cpp code
tip_povratne_vrijednosti ime_funcije(lista parametara) {
.
.
.
// Radimo nesto
.
.
.
return povratna_vrijednost;
}


Za tip_povratne_vrijednosti koristimo C++ tipove podataka( int, char, string... ), ili tipove podataka koje smo mi napravili ali o tome više nekad poslije. Taj tip mora biti isti kao i tip varijable povratna_vrijednost koju vraćamo ključnom riječju return.
Za ime_funkcije koristimo ime koje odgovara toj funkciji, i važe ista pravila kao i za imenovanje varijabli.
Za listu parametara koristimo C++ tipove podataka i dajemo im imena tj. pravimo lokalne varijble koje su "žive" sve dok se funkcija izvršava.
Funkcija ne mora imati parametre tako da to možemo ostaviti prazno.

Primjer1:
cpp code
#include <iostream>
using namespace std;

float povrsina_kruga(float poluprecnik) {
float povrsina;
povrsina = 2*poluprecnik*3.14;
return povrsina;
}
/* Povratna vrijednost moze biti i izraz tako da funkciju povrsina_kruga kraće možemo napisat:
float povrsina_kruga(float poluprecnik) {
return 2*poluprecnik*3.14;
}
*/
int main() {
float r, povrsina1, povrsina2;

cout<<"Unesite poluprecnik kruga"<<endl;
cin>>r;

povrsina1 = povrsina_kruga(r); // Primer poziva funkcije
povrsina2 = povrsina_kruga(4.5687); // Primer poziva funkcije

cout<<"Krug poluprecnika "<<r<<" ima povrsinu"<<povrsina1<<endl;
cout<<"Krug poluprecnika 4.5687 ima povrsinu"<<povrsina2<<endl;

return 0;
}


Vidimo implementaciju funkcije povrsina_kruga. Tip povratne vrijednosti je float( zbog mnozenja s 3.14 ), i varijabla koju vraća s return je isto tip float( mora biti ).
U telu funkcije računamo površinu kruga po formuli. Za to iskorištavamo lokalnu varijablu poluprecnik koja je parametar funkcije.
U main funkciji unosimo poluprečnik nekog kruga. Površinu tog kruga ćemo spremiti u varijablu povrsina1.
U pozivu funkcije prosljeđujemo poluprečnik r kojem smo prethodno dodelili neku vrijednost. Naša funkcija sada dobija vrijednost r čija se vrijednost kopira u lokalnu varijablu funkcije poluprecnik. To se zove prenos parametara po vrijednosti, a postoji i prenos parametara po referenci o kome ćemo govoriti posle. Funcija izvrši date naredbe tako da je vrijednost funkcije zapravo vrijednost varijable koju vraća, i ta se vrijednost dodjeljuje varijabli povrsina1.
Funkciju možemo pozvati i sa nekom vrijednosti koja odgovara tipu parametra kao što vidimo u primjeru.

Našu funkciju smo pozvali u funkciji main(). To je zbog pravila koje kaže da bi funkcija bila pozvana u nekoj drugoj funckiji mora biti deklarisana iznad te funkcije. Tako da sve naše funkcije pišemo iznad funkcije main().
Naše funkcije možemo deklarisati iznad funkcije main(), a implementirati ispod funkcije main() - ako je to nekome preglednije.

Primjer2:
cpp code
#include <iostream>
using namespace std;

int funkcija1( /* parametri */ ); // deklaracija ili protutip funkcije
int funkcija2( /* parametri */); // deklaracija ili protutip funkcije

int main() {
.
.
.
}
int funkcija1( /* parametri */ ) {
.
.
.
}
int funkcija2( /* parametri */ ) {
.
.
.
}




Funkcija main():

Nadam se da sada bolje razumete funkciju main(). Tip povratne vrijednosti je int. I mi vraćamo 0 kao povratnu vrijednost što jeste int. Ako main() vrati 0 to govori operativnom sistemu da je program izvršen i da nema grešaka. Ako ipak vrati vrijednost različitu od 0, onda se desila neka greška.



FUNKCIJE BEZ POVRATNE VRIJEDNOSTI:

Funkcije mogu biti i bez povratne vrijednosti. Tako da umesto tipa povratne vrijednosti pišemo void.

Primjer3:
cpp code
#include <iostream>
#include <string>

using namespace std;

void pozdrav(string ime) {
cout<<"Pozdrav "<<ime<<endl;
cout<<"Jos neki tekst"<<endl;
}
int main() {
string ime1;

cout<<"Unesite ime"<<endl;
cin>>ime1;

pozdrav(ime1);

return 0;
}


Primećujemo da je return izostavljen. To je zato što void funkcije ne vraćaju ništa pa je suvišan.
Funkcija pozdrav će ispisati:
Kod: Označi sve
Pozdrav [ime koje ste uneli]
Jos neki tekst



Evo kako možemo napisati triple Hello World program s prvog tutoriala.
Primjer4:
cpp code
#include <iostream>

using namespace std;

void hello() { // funkcija bez parametara
cout<<"Hello World!"<<endl;
}
int main() {
hello();
hello();
hello();

return 0;
}




DEFAULTNI PARAMETAR KOD FUNKCIJA:

U programskom jeziku C++ imamo veoma korisnu osobinu - defaultni parametar. Zadnji parametar u funkciji ili nekliko zadnjih mogu biti defaultni. Ako na mjesto defaultnog parametra u pozivu funkcije stavimo neku vrijednost ili varijablu onda se defaultna vrijednost prepisuje. A na mjesto defaultnog parametra u pozivu funkcije ne stavimo neku vrijednost ili varijablu onda je vrijednost parametra ta defaultna vrijednost.

Primjer5:
cpp code
#include <iostream>

using namespace std;

float deljenje(int a, int b = 2) {
return a/b;
}
int main() {
int m,n;
cout<<"Unesite brojeve za deljenje:"<<endl;
cin>>m>>n;

cout<<"m/n je"<<deljenje(m,n)<<endl;
cout<<"m/2 je"<<deljenje(m)<<endl; // deljenje(m) == deljenje(m,2)

return 0;
}




FUNCTION OVERLOADING:

U C++ imamo i mogućnost da više funkcija ima isto ime pod uslovom da se razlikuju po broju parametara ili po tipu parametara.

Primjer6:
cpp code
#include <iostream>

using namespace std;

int delenje(int a,int b) {
return a/b;
}
double delenje(double a,double b) {
return a/b;
}
int main() {

cout<<"5/4 (cjelobrojno) je"<<delenje(5,4)<<endl; // Pozivamo prvu funkciju
cout<<"5.0/2 je"<<delenje(5.0,4)<<endl; // Greska, delenje(double, int) je nejasno!!!
cout<<"5.0/4.0 je"<<delenje(5.0,4.0)<<endl; // Pozivamo drugu funkciju, 5.0 i 4.0 su tipa float ili double
cout<<"7.45/3.78 je"<<delenje(7.45,3.78)<<endl; // Pozivamo drugu funkciju

return 0;
}


Ako imamo situaciju da kompajler može pozvati obe fukcije( poziv je nejasan ) onda ćemo dobiti grešku od kompajlera!
To se lako može desiti ako koristimo defaultni parametar kod funkcija koje imaju isto ime. Tako da, pazite na to.



GENERIČKE FUNKCIJE:

C++ podržava i generičko programiranje, tako da možemo pisati generičke funkcije koju su veoma korisne. Kod generičkih funkcija tip povratne vrijednosti ili bilo koji parametar je neki tip T koji će se definisati kod poziva funkcije tj. tip nije definisan.

Primjer7:
cpp code
#include <iostream>

using namespace std;

template <typename T>
T delenje(T x,T y) {
return x/y;
}

int main() {
cout<<"8/4 je"<<delenje(8,4)<<endl; // T je int
cout<<"4.45/7.85 je"<<delenje(4.45,7.85)<<endl; // T je double
cout<<"15/3.5 je"<<delenje(15,3.5)<<endl; // Greska, nema funkcije delenje(int, double)

return 0;
}


Kada kompajler naiđe na poziv generičke funkcije npr. delenje(8,4) on će generisati funkciju int delenje(int x, int y); i koristiti nju za taj i pozive s istim tipom. Kod delenje(4.45,7.85) ce uraditi isto.
Grešku vjerujem razumijete.

Možemo imati više "nepoznatih tipova" i možemo stavljati "poznate" tipove u funkcije.

Primjer8:
cpp code
#include <iostream>

using namespace std;

template <typename T, typename R>
double delenje(T x,R y) {
return x/y;
}

int main() {
cout<<"8/4 je"<<delenje(8,4)<<endl; // T je int
cout<<"4.45/7.85 je"<<delenje(4.45,7.85)<<endl; // T je double
cout<<"15/3.5 je"<<delenje(15,3.5)<<endl; // Greska, nema funkcije delenje(int, double)

return 0;
}


Sada funkcija delenje() uvijek vraća double, neovisno od parametara koje pošaljemo u pozivu.


To je to o funkcijama, za sada. Kada obradimo pointere/reference saznati ćemo šta još možemo uraditi s funkcijama.


11 post(ov)a • Stranica: 2/2.1, 2

Na mreži

Trenutno korisnika/ca: / i 1 gost.