Download as pdf or txt
Download as pdf or txt
You are on page 1of 109

Bazat e gjuhës programuese C++ S.

Bekteshi 3

Bazat e gjuhës programuese

C++

Përpunuar nga:
Dr. Sadik Bekteshi
Bazat e gjuhës programuese C++ S. Bekteshi 4

Përmbajtja

1. KUPTIMET THEMELORE TË PROGRAMIMIT ......................................................................... 7


Algoritmet ...................................................................................................................................7
Diagramet e rrjedhjes së programit.............................................................................................8
Tipet e gjuhëve programuese ....................................................................................................10
Procesi i përkthimit të programit ..............................................................................................11

2. BAZAT E GJUHËS C++.......................................................................................................... 12


Tërësia e karaktereve ................................................................................................................12
Fjalët e rezervuara.....................................................................................................................12
Emërtimet..................................................................................................................................12
Shprehja ....................................................................................................................................13
Urdhëresa ..................................................................................................................................13
Elementet themelore të gjuhës C++..........................................................................................14
Hyrja dhe dalja elementare .......................................................................................................15

3. TIPET THEMELORE TË TË DHËNAVE ................................................................................... 20


Ndryshoret dhe komstantet .......................................................................................................20
Tipi int.......................................................................................................................................22
Deklarimi i ndryshoreve të tipit int.....................................................................................22
Dhënja e vlerave ndryshoreve (inicializimi).......................................................................22
Tipi signed, unsigned, short ose long int ............................................................................23
typedef.......................................................................................................................................24
Tipi float dhe double.................................................................................................................24
Deklarimi i ndryshoreve me presje dhjetore .......................................................................25
#define.......................................................................................................................................25
const ..........................................................................................................................................26
Notacioni shkencor ...................................................................................................................26
Tipi char ....................................................................................................................................27
Ndryshoret e tipit char ..............................................................................................................28
Konstantet e tipit char ...............................................................................................................28
Karakteret e kalimit (escape characters) ...................................................................................29
Operatori cast ............................................................................................................................30

4. KONTROLLIMI I RRJEDHJES SË PROGRAMIT.................................................................... 31


Operatorët .................................................................................................................................31
Operatori për dhënjen e vlerave ..........................................................................................31
Operatorët dhe shprehjet aritmetike....................................................................................32
Operatorët e inkrementimit dhe dekrementimit ................................................................33
Operatorët dhe shprehjet krahasuese (relacionale) .............................................................34
Operatorët dhe shprehjet logjike.........................................................................................35
Operatori i shprehjes së kushtëzuar ....................................................................................37
Bazat e gjuhës programuese C++ S. Bekteshi 5

5. RRJEDHJA E PROGRAMIT DHE DREJTIMI I EKZEKUTIMIT ............................................... 39


Strukturat e kontrollit................................................................................................................39
Struktura zgjedhëse if .........................................................................................................39
Struktura zgjedhëse if-else..................................................................................................40
Formulimi i algoritmeve .....................................................................................................43
Struktura përsëritëse (cikli) while.......................................................................................45
Struktura përsëritëse do-while ............................................................................................46
Ciklet e përfshira.................................................................................................................47
Struktura përsëritëse for ......................................................................................................51
Struktura e zgjedhjes së shumëfishtë switch.......................................................................55
Urdhëresat break dhe continue............................................................................................55

6. FUNKSIONET, NDRYSHORET DHE FUSHËVEPRIMI I TYRE.............................................. 57


Funksionet dhe ekzekutimi i tyre..............................................................................................57
Deklarimi (prototipi) dhe definimi i funksioneve ...............................................................58
Definimi i funksionit...........................................................................................................58
Kreu i funksionit .................................................................................................................58
Lista e parametrave .............................................................................................................59
Trupi i funksionit ................................................................................................................59
Deklarimi i funksionit .........................................................................................................61
Prototipi i funksionit ...........................................................................................................61
Fajllat header.......................................................................................................................62
Parametrat dhe argumentet e funksionit .............................................................................63
Thirrja dhe kthimi i funksioneve.........................................................................................64
Dërgimi përmes vlerës ........................................................................................................66
Kthimi i vlerave me return .................................................................................................68
Ndryshoret dhe fushëveprimi i tyre ..........................................................................................70

7. MATRICAT ............................................................................................................................. 76
Matricat njëdimensionale..........................................................................................................76
Deklarimi i matricës............................................................................................................76
Inicializimi i matricës .........................................................................................................77
Klasifikimi i matricave .......................................................................................................78
Matricat dhe funksionet ............................................................................................................79
Matricat shumëdimensionale ....................................................................................................80
Inicializimi i matricave shumëdimensionale ............................................................................80

8. TREGUESIT ........................................................................................................................... 84
Ruajtja e adresës në tregues ......................................................................................................84
Deklarimi i treguesve ................................................................................................................84
Operatori i adresës ....................................................................................................................85
Operatori i indireksionit............................................................................................................86
Shprehjet dhe aritmetika me ndryshore të tipit tregues ............................................................86
do të jep 3008 (3000+2*4) nëse një integer është ruatur në 4 bajt të memorjes.................87
Marrëdhënja në mes të matricave dhe treguesve ......................................................................87
Treguesit në funksione ..............................................................................................................88

9. STRINGJET............................................................................................................................ 89
Bazat e gjuhës programuese C++ S. Bekteshi 6

10. KLASA .................................................................................................................................. 91


Deklarimi i klasës .....................................................................................................................91
Definimi i objektit.....................................................................................................................92
Çasja e anëtarëve të klasës........................................................................................................93
Përdorimi i fjalëve të rezervuara public dhe private.................................................................93
Implementimi i metodës së klasës ............................................................................................95
Konstruktorët dhe destruktorët .................................................................................................97
Konstruktorët dhe destruktorët default ....................................................................................97
Ndarja e interfejsit nga implementimi ....................................................................................100
Përfundim:...............................................................................................................................100
Programimi i orientuar në objekte. .........................................................................................101
Fushëveprimi i klasës dhe çasja në anëtarët e klasës ..............................................................104

SHTESA.1 LOKACIONET E MEMORJES ................................................................................. 105

SHTESA.2 QARQET LOGJIKE ................................................................................................. 107


Operacionet logjike .................................................................................................................107
Operacionet elementare .........................................................................................................108
Operacioni OSE ................................................................................................................108
Operacioni EDHE .............................................................................................................108
Operacioni JO ...................................................................................................................109
Operacioni logjik JOOSE .................................................................................................109
Operacioni logjik JOEDHE ..............................................................................................110
Operacioni logjik EX-OSE ...............................................................................................110
Operacioni logjik EX-JOOSE...........................................................................................110
Bazat e gjuhës programuese C++ S. Bekteshi 7

1. Kuptimet themelore të programimit


Algoritmet

Para se të shkruhet një pogram për zgjidhjen e një problemi është me rëndësi që problemi të
kuptohet plotësisht dhe zgjidhja e tij të planifikohet me kujdes. Zgjidhja e një problemi duhet të
definohet në formë të një procedure të caktuar.
Agoritmi paraqet procedurën ose metodën e zgjidhjes së një problemi në bazë të:
- aksioneve që do të ekzekutohen dhe
- radhës sipas të cilit këto aksione do të ekzekutohen.
Përcaktimi i radhës sipas të cilës do të ekzekutohen në programin e kompjuterit quhet kontrolla
e programit. Në formimin e algoritmeve përdoret një gjuhë artificiale dhe informuese që i ndihmon
programuesit që quhet pseudokod.
Shembull: Të supozojmë se duhet të caktojmë se cili nga numrat pozitiv a dhe b e ka vlerën më të
madhe. Pseudokodi është si vijon:
 numri b të zbritet nga numri a respektivisht të gjendet a-b;
 nëse ndryshimi a-b është më i madh se zero atëhere numri a është më i madh se numri b;
 nëse ndryshimi a-b është më i barabartë me zero atëhere numri a është i barabartë me
numrin b;
 nëse ndryshimi a-b është më i vogël se zero atëhere numri a është më i vogël se numri b.
Kompjuteri nuk e kupton pseudokodin (algoritmin tekstual) e këtillë. Pseudokodet nuk
ekzekutohen në kompjuter. Ato vetëm i ndihmojnë programuesit të “mendojë” për programin para
se ta shkruaj atë. Pseudokodi i përgaditur me kujdes lehtë mund të shëndrrohet në program thjesht
duke i zëvendësuar urdhëresat e pseudokodit me ekuivalentet e tyre të C++. Pseudokodi përmban
vetëm urdhëresat ekzekutabile.

Shembull: Deklaratat nuk janë urdhëresa ekzekutabile, psh deklarata:


int x;
vetëm i tregon kompajllerit tipin e ndryshores dhe se duhet të rezervoj hapësirë në memorje për
ndryshoren x. Por kjo deklaratë nuk shkakton asnjë aksion as në hyrje as në dalje as në llogaritje –
kur ekzekutohet programi.

Që algoritmi të realizohet në kompjuter duhet të paraqitet me urdhëresat të cilat i “kupton”


kompjuteri
Program quhet sekuenca e urdhëresave të tilla ndërsa gjuha në të cilën bëjnë pjesë ato
urdhëresa quhet gjuhë programuse (sa për ilustrim të themi se programi për pseudokodin e
mësipërm është paraqit në prg5). Ngjashëm me gjuhën e folur, gjatë shkruarjes së programit,
programuesi duhet t’i përmbahet rregullave dhe konstruksioneve të caktuara gramatikore
respektivisht sintaksës së gjuhës programuese.
Bazat e gjuhës programuese C++ S. Bekteshi 8

1. // prg5
2. #include <iostream.h>
3. int main()
4. {
5. int num1, num2; // deklarata
6. cout << "Shtypni dy numra: "; // kërkon
7. cin >> num1 >> num2; // ti shtypim dy numra
8. if ( num1 == num2 )
9. cout << "Numrat janë të barabartë." << endl;
10. if ( num1 > num2 )
11. cout << num1 << " është më i madh." << endl;
12. if ( num2 > num1 )
13. cout << num2 << " është më i madh." << endl;
14. return 0;
15. }
Dalja: Shtypni dy numra 3 8
8 është më i madh

Diagramet e rrjedhjes së programit

Njëra nga mënyrat më të mira për punimin e programit është vizatimi i


diagramit të rrjedhjes në të cilin paraqitet secili hap logjik i programit dmth në Fillimi ose mbarimi
mënyrë grafike e paraqitet qartë tërë procesi përpunimit të të dhënave. i programit
Rrjedhjen e programit dmth radhën e kryerjes së të gjitha operacioneve e
paraqesim me diagramin e rrjedhjes. Qëllimi i diagramit të rrjedhjes është që
t’a paraqes në mënyrë sa ma të qartë rrjedhjen e ekzekutimit të programit.
Pra. diagrami i rrjedhjes (angl. flowchart) është paraqitje grafike e një Përpunimi i të
dhënave
algoritmi ose e një pjese të algoritmit. Në mënyrë që të kemi sa më pak tekst
këto diagrame paraqiten me simbole të cilat gjithëmonë e kanë domethënjen e
njejtë. Fatkeqsisht këto simbole nuk janë të standardizuara Simbolet të cilat
përdoren në diagramet e rrjedhjes janë katërkëndshat, elipsat dhe rrathë të Nënprogrami
vegjël të cilat janë paraqitur në fig.1. Këto simbole lidhen me shigjeta që
quhen vijat e rrjedhjes. Sikurse edhe pseudokodet, diagramet e rrjedhjes janë
shumë të përshtatshme për formimin dhe paraqitjen e algoritmeve edhepse
pseudokodi preferohet më shumë prej programuesve. Sjellja e vendimeve
Simboli i katërkëndëshit që quhet edhe simboli i aksionit tregon për çdo
tip të aksionit duke përfshi llogaritjet ose një operacion hyrës/dalës. Vijat e
rrjedhjes në diagramin e rrjedhjes tregojnë radhën sipas të cilës kryhen
aksionet. Hyrja ose dalja

Shembull: Në diagramin e rrjedhjes në fig.2 radha e kryerjes së operacioneve


shkon (në kahje të shigjetës) në këtë mënyrë: së pari shuma i shtohet vlerës e
pastaj 1 i shtohet sasisë. Modifikimi

Kur ta vizatojmë diagramin e rrjedhjes i cili paraqet algoritmin


komplet, një simbol elipsë i cili e përmban fjalën “fillimi” ësktë simboli i parë Shigjetat paraqesin
ndërsa simboli i fundit që përdoret është simboli elipsë i cili e përmban fjalën radhën e ekzekutimit
të operacioneve
“fundi”. Kur të vizatojmë vetëm një pjesë të algoritmit simbolet ovale
Fig.1
Bazat e gjuhës programuese C++ S. Bekteshi 9

mungojnë dhe përdoren vetëm rrathë të vegjël që quhen simbolet lidhëse. Prej të gjitha simboleve
ndoshta më i rëndësishmi është simboli diamond i cili quhet edhe simbol i vendosjes që tregon për
vendimet që do të mirren. Për këtë simbol do të bëhet fjalë edhe më vonë.
Diagramin e rrjedhjes duhet t’a vizatojmë në atë mënyrë që një vizatim të paraqes një tërësi
të plotë. Nëse programi është i madh ai duhet të ndahet në nënprograme ose “blloqe” të cilat
vizatohen tërësisht në vizatime të veqanta.
Diagrami i rrjedhjes paraqet dokumentin
themelor që duhet të jetë i detajuar në mënyrë që të
mundemi drejpërdrejt nga ai të shkruajmë programin. I shton shumën vlerës vlera=vlera+shuma;
Është mirë që në diagramin e rrjedhjes të shënohen
sqarime ose vërejtje të cilat në program do të
paraqiten si komente. Kjo ndihmon shumë gjatë I shton 1 sasisë Sasia= Sasia +1;
testimit dhe përpunimit të programit.
Përveç simboleve të theksuara mund të
përdoren edhe simbole tjera simbas zgjedhjes
personale duke pasur parasysh ato që u theksuan më Fig.2
lartë.
Bazat e gjuhës programuese C++ S. Bekteshi 10

Tipet e gjuhëve programuese

Gjuhët programuese me të cilat mund të programohet ndahen në disa tipe në varshmëri nga
urdhëresat që disponojnë.
- Gjuhët e makinës
- Gjuhët assembler
- Gjuhët të nivelit të lartë
Gjuha e makinës është gjuha themelore. Gjuha e makinës është “gjuha natyrore” e çdo
kompjuteri, është e vetmja gjuhë të cilën e “kupton” kompjuteri dhe të cilën e realizon. Ajo është e
definuar nga dizajni hardverik i kompjuterit. Gjuhët e makinës gjithmonë përmbajnë vargjet e
numrave ( të 1-ve dh 0-ve) që e udhëzon kompjuterin që të kryejnë operacionet e tyre elementare
një nga një. Gjuhët e makinës janë gjuhë të varura nga makina që dmth se një gjuhë specifike e
makinës mund të përdoret vetëm në një tip të kompjuterit. Programimi në gjuhën e makinës është i
vështirë për përdorim dhe mundëson gabime të shumta.
Gjuha assembler - në vend që të përdoren vargjet e numrave shumë më e përshtatshme është që
të përdoren fjalë (anglishte) që paraqesin operacionet elementare të kompjuterit. Këto fjalë kanë
formuar bazën e gjuhëve assembler. Gjuha assembler ose gjuha simbolike mundëson shfrytëzimin
më të lehtë të gjuhës së makinës me futjen e emrave simbolik për urdhëresa dhe adresa të
lokacioneve të memorjes Programet përkthyese të quajtura assemblerë ishin zhvilluar që të kthejnë
instruksionet e shkruara në gjuhën assembler në urdhëresa të gjuhës së makinës. Në gjuhët
assembler korrespondenca ndërmjet gjuhës assembler dhe gjuhës së makinës është 1 me 1.
Programuesi i përdor urdhëresat e kompjuterit në të cilin punon dhe për këtë arsye programi nuk
mund të bartet në kompjuter tjetër (programi nuk mund të ekzekutohet në kompjuter tjetër pa u
riprogramuar).
Gjuhët programuese të nivelit të lartë (Fortran, Basic, Pascal, Cobol etj) i eliminojnë këto
probleme. Gjuha porgramuese e nivelit të lartë nuk varet nga kompjuteri. Programet e shkruara në
këto gjuhë janë të bartshëm (programi mund të ekzekutohet në kompjuter tjetër pa u riprogramuar)
kështu që programi mund të ekzekutohet në tipe të ndryshme të kompjuterëve. Kësaj i ka kontribuar
edhe standardizimi i sintaksës së gjuhës së lartë. Një urdhëresë e gjuhës së nivelit të lartë është
ekuivalente me grup të urdhëresave të gjuhës së makinës. Për këtë arsye është paraqitë nevoja që të
automatizohet procesi i përkthimit të urdhëresave të gjuhës së lartë në urdhëresat e gjuhës së
makinës.
Programet përkthyese që quhen compilers e konvertojnë gjuhën e nivelit të lartë në gjuhën e
makinës. Gjuhët e nivelit të lartë i lejojnë programuesit ti shkruajnë instruksionet në anglishte dhe
përmbajnë notacionin e zakonshëm matematik. Gjuhët C dhe C++ janë gjuhët ndër gjuhët më të
fuqishme dhe që përdoren më së shumti. Procesi i kompajllimit të gjuhës së nivelit të lartë në
gjuhën e makinës zakonisht merr një kohë të caktura. Programet interpreter i ekzekutojnë
drejtpërsëdrejti programet në gjuhën e nivelit të lartë pa pasur nevojë për kompajllimin e këtyre
programeve në gjuhën e makinës.
Programet, assemblerët dhe përkthyesit ekzekutohen në kompjuter në praninë e rrethinës së
caktuar. Këtë rrethinë e përcakton sistemi operues. Siç kemi thënë edhe më parë sistemi operues
është tërësi e programeve të cilat udhëheqim me resurset dhe serviset e sistemit kompjuterik siç
janë: memorjet, procesorët, pajisjet hyrëse/dalëse etj. Programi në mënyrë implicite ose eksplicite
me ndihmën e urdhëresave të sistemit ooperues mund t’i shfrytëzoj resurset e sistemit kompjuterik.
Në këtë mënyrë mundësohet dhe realizohet ekzekutimi i programit.
Bazat e gjuhës programuese C++ S. Bekteshi 11

Procesi i përkthimit të programit

Në figurën 3 është paraqitur një proces tipik i futjes, përkthimit dhe ekzekutimit të
programit të shkruar në gjuhën e nivelit të lartë. Programi i cili duhet të përkthehet duhet të futet në
kompjuter dhe të vendoset në mediumet e memorjes në formë të fajllit. Kjo realizohet me ndihmën
e editorit të tekstit e cila i përmban urdhëresat me ndihmën e të cilave e shtypim tekstin e programit.
Si rezultat i editorit është fajlli në formën burimore të programit e cila quhet programi burimor.
Hyrja në përkthyes është programi burimor. Rezultati ose dalja e përkthyesit fajlli me
programin e përkthyer burimor që quhet program i objektit.
Përkthimi kryhet më së shpeshti në dy faza. Faza e parë është përkthimi i programit burimor
në program ekuivalent assembler ndërsa e dyta
assemblimi i programit të fituar në program të
Fillimi i procesit
makinës. Disa përkthyes në mënyrë automatike e
thërrason assemblerin pas fazës së parë e disa jo. Në
rastin e dytë, programuesi duhet në mënyrë Futja e programit
eksplicite të jep urdhëresën për assenblim. Gjatë (editori)
përkthimit të programit burimor përkthyesi mund të
sinjalizoj prezencën e gabimeve në programin Përkthimi
burimor. Programi i objektit është hyrje në linker
(lidhës).
Linkeri është program sistemor që ka për Gabimi
detyrë që programin e objektit e eventualisht
programet e objekteve nga biblioteka sistemore si
edhe programet e përkthyera më parë t’i lidh me Biblioteka sistem. Linkimi (lidhja)
programin ekzekutues të cilin kompjuteri (sistemi
operativ) mund t’a ekzekuton. Linkeri mund të Ekzekutimi
thirret automatikisht në fazën e përkthimit. Në disa
sisteme kjo mundësi nuk ekziston kështu që linkimi
duhet të kryhet me urdhëresë eksplicite nga sistemi Gabimi
operativ.
Programi ekzekutues i fituar pas fazës së
linkimit është i gatshëm për ekzekutim. Programi Mbarimi i procesit
ekzekutues starton me urdhëresë nga sistemi
operues. Gjatë kësaj kohe ai pranohet nga mbushësi Fig.3
i cili programin e vendos në memorjen operuese
RAM, i rezervon resurset e sistemit dhe programin ekzekutues ia dorëzon sistemit operues.
Programi ekzekutues në zhvillimet e mëtejshme është nën kontrollën e sistemit operues.
Nëse programi gjatë ekzekutimit nuk jep rezultatet e kërkuara duhet që të përmirsohet
programi burimor dhe përsëri të kryhet përkthimi dhe lidhja.
Bazat e gjuhës programuese C++ S. Bekteshi 12

2. Bazat e gjuhës C++


Në këtë kapitull janë paraqitur elementet themelore përbërëse të gjuhës C++. Ato janë
tërësia e karaktereve, fjalët e rezervuara (angl. keywords), shprehjet, deklaratat, operatorët,
funksionet, ndryshoret dhe konstantet. Janë dhënë programe komplete të cilat përmbajnë elementet
e definuara.

Tërësia e karaktereve

Karakteret e lejuara për formimin e elementeve themelore të programit C++ janë:


 karakteret alfanumerike (shkronjat e vogla dhe të mëdha dhe numrat)
 karakteret speciale dhe
 karakteret e padukshme (tabela.1).
Në shumicën e gjuhëve programuese (Fortran, Cobol, Basic etj) shkronjat e vogla dhe të
mëdha trajtohen njësoj. Në gjuhën C++ ato nuk trajtohen njësoj, kështu psh Fizika, fizika dhe
FIZIKA janë simbole të ndryshme.

Fjalët e rezervuara

Fjalët e rezervuara (keywords) kanë një kuptim të definuar që më parë, kështu që nuk mund
të përdoren në konteste tjera. Fjalët e rezervuara nuk lejohet të përdoren si identifikatorë si psh
emër i ndonjë ndryshoreje. Karakteristikë e gjuhës C++ është përdorimi vetëm i shkronjave të vogla
për shkruarjen e fjalëve të rezervuara. Kjo gjuhë ka një numër relativisht të vogël të fjalëve të
rezervuara në krahasim me gjuhët tjera por me këtë mundëstë e saj nuk janë zvogluar (tabela.2).

Tabela 1. Fjalët e rezervuara (keywords) në C++

auto const double float int short struct unsigned


break continue else for long signed switch void
case default enum goto register sizeof typedef volatile
char do extern if return static union while

Emërtimet

Emërtimet (identifikatorët) përdoren për dhënjen e emrave objekteve (ndryshoreve,


funksioneve etj.) në program. Identifikatorët janë sekuencë e:
- Shkronjave të mëdha dhe të vogla (nga A deri në Zh),
- Numrave (0 deri në 9) dhe të cilët mund të jenë në çdo pozitë përveç si karakter i parë.
- Karakterit „ – „ (vija e poshtme).
Nuk lejohet që:
- Emërtimi të përmbaj simbolet matematike,
- Emërtimi të përmbaj fjalë të rezervuara ose emrat e unksioneve të bibliotekës standarde të
C+
- Emërtimi të përmbaj karaktere speciale si @, #, $ etj,
- Emërtimi të përmbaj asnjë pikë ose apostrof ose karakter të zbrazët (blank).
Bazat e gjuhës programuese C++ S. Bekteshi 13

Me qëllim që të rritet lexueshmëria dhe dokumentimi i programit preferohet që


identifikatorët të jenë të thjeshtë dhe domethënës (psh për të treguar sipërfaqen e rrethit përdoret
identifikatori sipërfaqja). Numri i karaktereve në emërtim nuk është i kufizuar por në shumë
sisteme numri i karaktereve kryesore është i kufizuar në 31. Kjo dmth se kompajlleri i shiqon vetëm
31 karakteret e parë të emërtimit.

Shembull. Identifikatorët e shkruar:


- drejt x, z_256, shuma, _tabela, EmriStudent, matja1,
- të papërshtatshëm V235xt, aaaifjktnnt, int1
- gabim min+1, 2_matja , $paga, 4356, int, ndryshorja 1,
+sipërfaqja
min+1 nuk është identifikator por shprehje sepse përmban shenjën “+“, 2_matja është gabim sepse
fillon me numër, $paga sepse fillon me karakter special, 4356 është numër, int sepse është fjalë e
rezervuar, ndryshorja 1 sepse është e ndarë ndryshorja nga 1 dhe +sipërfaqja sepse është shprehje.

Shprehja

Çdo gjë që jep si rezultat një vlerë paraqet shprehje në C++. Të gjitha shprehjet janë
urdhëresa. Kombinimi i operandëve (ndryshoreve dhe konstanteve) dhe operatorëve formon
shprehjen. Shprehja i kryen llogaritjet dhe jep një rezultat i cili shkakton një aktivitet. Një shprehje
thuhet se e kthen vlerën.

Shembull: Shprehja:
1. 3.2 // e kthen vlerën 3.2
2. PI // e kthen vlerën 3.14
3. x = a + b;
Shprehja e fundit, përkundër algjebrës, nuk domethanë se x është i barabartë me a+b por
vlera e a e mbledhë me vlerën e b dhe rezultati i fituar i jipet x. Pasi kemi të bëjmë me shprehje ajo
e kthen vlerën e x.

Me shprehje është e mundshme të specifikohen kombinime të këtyre detyrave kurse në


aplikimet më të përparuara shprehjet mund të përdoren edhe për shenjëzimin e objekteve ose
funksioneve.

Urdhëresa

Në C++ urdhëresa kontrollon radhën e ekzekutimit, e zhvillon (evaluates) një shprehje ose
nuk bën asgjë (urdhëresa null). Pikëpresja është shenja për fundin (mbarimin) e urdhëresës.
Urdhëresë themelore është shprehja pas të cilës vjen pikëpresja dhe klasifikohet si urdhëresë e tipit
të shprehjes..

Shembull: Disa shembuj të urdhëresave


i = (2 + 3) * 10;
i = 2 + 3 * 10;
j = 6 % 4;
k = i + j;
return 0;
exit(0);
Bazat e gjuhës programuese C++ S. Bekteshi 14

Urdhëresat sipas rregullës ekzekutohen sipas radhës së paraqitjes së tyre në program. Radha
e ekzekutimit megjithate mund të ndryshohet me urdhëresat të cilat e bartin rrjedhjen e programit
në një pjesë tjetër ose jasht programit.
Urdhëresa e përbërë e cila poashtu quhet edhe blok urdhëresë është mekanizëm i cili grupon
disa urdhëresa në një tërësi sintaksore. Grupi i urdhëresave që formojnë blok urdhëresën duhet të
futet brenda kllapave të mëdha. Blok urdhëresa trajtohet si një urdhëresë nga kompajlleri i C++.
Bloqet mund të jenë të përfshira dhe secili mund të përmbaj pos urdhëresave ekzekutuese,
deklaratat dhe inicializimet vetjake.

Shembull: Një blok urdhëresë që është e vendosur brenda kllapave të mëdha {}e ka formën:
for(. . .) {
s3 = s1 + s2;
mul = s3 * c;
mbetja = shuma % c;
}

Lista e mëposhtme paraqet sintaksën e urdhëresave të cilat i formojnë funksionet dhe


programet.

Elementet themelore të gjuhës C++


Gjuha C++ përbëhet prej elementeve themelore ndërtuese: shprehjeve, deklaratave,
operatorëve, funksioneve etj. Do t’a analizojmë një program të thjeshtë:

1. prg1
2. #include <iostream.h>
3. int main()
4. {
5. cout << "Programi im i pare ne C++!\n";
6. return 0; /*tregon se programi përfundon me sukses*/
7. }
Dalja: Programi im i pare ne C++!

Funksionet main dhe cout janë emrat e funksioneve sistemore. Funksioni main e informon
sostemin se ku fillon ekzekutimi i programit ndërsa kllapat () tregojnë se funksioni main nuk ka
argumente. Në programin C++ duhet të ekzistoj vetëm një main() sepse programi nuk mund të filloj
ekzekutimin në disa vende njëkohsisht. Fjala e rezervuar int majtas main tregon se main “kthen”
vlerë të tipit int (numër të plotë). Kllapa e madhe { e fillon trupin e çdo funksioni; në këtë rast edhe
të funksionit main kurse kllapa e madhe e djathtë } tregon mbarimin e trupit respektivisht fundin e
funksionit main.
cout (lexo si-out) është funksion për shtypjen e vargut të karaktereve që gjenden në mes të
thojzave në ekran, në rastin tonë të lajmërimit “Programi im i parë në gjuhën C++”.
cout << “Programi im i parë në gjuhën C++”; është një urdhëresë dhe paraqet përpunimin
elementar të cilin duhet t’a kryej programi. Karakteri << quhet operatori i futjes së stream-it. Kur
programi ekzekutohet, vlera që gjendet djathtas operatorit, operandi i djathtë, futet në stream-in
dalës. Karakteret që gjenden në operandin e djathtë shtypen saktë ashtu si paraqiten brenda
thojzave. Karakteri pikëpresje“;” e luan rolin e terminatorit të urdhëresës.
Bazat e gjuhës programuese C++ S. Bekteshi 15

Karakteri \n nuk shtypet në ekran. Karakteri \ kundërpjerrtë (viza kundër e pjerrtë,


backslash) quhet karakter i kalimit (escape) dhe tregon se si një karakter “special” do të paraqitet në
dalje. Backslash së bashku me karakteret që vijnë pas formojnë sekuencën e kalimit. Sekuenca e
kalimit \n ( “\”dhe “n” së bashku) paraqet një karakter “\n” që paraqet rreshtin e ri dhe shkakton që
kursori të çxendoset në rreshtin e ri në ekran që dmth se programi C++ shtypjen vijuese e kryen në
rresht të ri.
#include <iostream.h> paraqet urdhëresë preprocesorike dmth një mesazh për preprocesor.
Rreshtat që fillojnë me # procesoohen nga preprocesori para se të kompajllohet programi. Rreshti i
theksuar e drejton preprocesorin të përfshijë (të fut) në program përmbajtjet e fajllit input output
stream header shkurt. iostream.h.. Ky fajll duhet të përfshihet në çdo program i cili të dhënat i
paraqet në ekran ose të dhënat i pranon nga tastatura.
Komenti paraqet tekstin pas karakterit // ose në mes të karaktereve /* dhe */ dhe nuk është
pjesë e programit ekzekutues. Në programin prg1 janë përdorë të dy llojet e komenteve:
Rreshti 1. //prg1
Rreshti 7. /*tregon se programi përfundon me sukses*/.
Nëse përdoret mënyra e parë atëhere në fillim të çdo rreshti të ri duhet të shkruhet simboli //
kurse nëse përdoret mënyra e dytë simbolo /* shkruhet në fillim ndërsa */ në fund të komentit pa
marrë parasysh se sa rreshta është i gjatë komenti. Komentet shkruhen me qëllim që të rritet
lexueshmëria e programit dmth të bëhet e qartë se si punon programi, zbatimet dhe kufizimet e tij.
Programuesit me përvojë nuk kursejnë në shkruarjen e komenteve.
Rreshti return 0; shkruhet në fund të fuksionit main(). Fjala e rezervuar return është njëra nga
disa mënyrat që përdoren për dalje nga funksioni. Kur urdhëresa return përdoret në fund të main()
siç është paraqitë këtu xlera 0 tregon se programi ka përfunduar me sukses.
Në fund të theksojmë se gjuha C++ nuk është pozicionale si p.sh gjuha Fortran (deklaratat
mund të shkruhen kudo në një ose më shumë rreshta. Programi në prg2 është plotsisht i njejtë me të
parin.

1. //prg2
2. #include <iostream.h> int main(){cout << "Programi im i pare ne C++!\n";
3. return 0; // tregon se programi përfundon me sukses }

Natyrisht programet nuk duhet të shkruhen në këtë stil për hirë të lexueshmërisë dhe
dokumentimit të programit.

Hyrja dhe dalja elementare

Në iostream.h janë të definuara cout dhe cin. Nëse ky fajll header është i përfshirë atëhere
mund të kryhen H/D me cout dhe cin. cout dhe cin quhen objekte. Në terminologjinë e C++ objekti
është i ngjashëm me ndryshoren, në këtë rast tipi i të dhënave është fajlli në vend të një integeri ose
karakteri. cout përdoret së bashku me karakterin << ndërsa cin me operatorin >>. Operatori <<
quhet operator i dhënjes sepse i jep të dhënat në ekran (i fut të dhënat në te) ndërsa operatori >>
quhet operator i nxjerrjes sepse i nxjerr nga tastatura (i mmerr të dhënat prej saj)
Opsionet e daljes – Me anë të cout shtypim në ekran tipin e të dhënave integer, float si dhe vargun
e karaktereve brenda thojzave.

Shembull: a) cout jep në dalje integer:


cout << 45; // Shtyp 45
Bazat e gjuhës programuese C++ S. Bekteshi 16

// cout jep në dalje numrat me presje dhjetore:


cout << 1.234567; // Shtyp 1.234567
/ cout jep në dalje stringun:
cout << "Une mesoj C++"; // Shtyp Une mesoj C++

Me anë të manipulatorit H/D mund të modifikohet mënyra e punës së cout. Zakonisht


manipulatori nevoitet kur në dalje kemi vlera numerike.

Shembull: b) Një ndryshore e tipit float gjithëmonë ka saktësinë prej gjashtë shifrave kështu që
kur të shtypet 4.5 si:
cout << 4.5;
C++ shtyp 4.500000.

Manipulatori i daljes që quhet precision() e kufizon saktësinë e daljes e cout. Brenda


kllapave të precision() me integer ose ndryshore përcaktohet se me sa shifra duhet të jetë dalja. Në
rastet kur shfrytëzuesi gabon në futjen e të dhënave urdhëresa ignore() i fshin ato të dhëna.

Shembull: c) Që të sigurojmë zeron e lëvizhne duhet të vendoset shenja (flag) e cout. Psh:
cout.setf(ios::fixed); // vendos shenja (flag) e cout për pike fikse
cout.setf(ios::showpoint); // Gjithëmonë e paraqet pikën dhjetore
cout.precision(2); // Dy shifra dhjetore
cout << 4.5;
shtyp 4.50 në ekran.
cin.ignore(80, '\n'); // Ifshin të dhënat hyrëse
Nëse saktësia është ndryshuar me precision(), saktësia e zakonshme prej gjashtë numrash
kthehet me urdhëresëm:
cout.precision(0); // E rikthen saktësinë e nënkupruar prej gjashtë numrash
ose
cout.precision(6); // E vendos saktësinë e nënkupruar prej gjashtë numrash

C++ përdor hapësirë të nevojshme për shtypjen e numrave.

Shembull: d) Psh dy hapësia të daljes për dy numra, tri hapësira të daljes për tre numra etj.
Manipulatori () përdoret për shtimin e hapësirave në dalje. Urdhëresat vijuese cout tregojnë se çka
është e mundshme me width():
cout.setf(ios::fixed);
cout.setf(ios::showpoint);
cout << 4.56 << endl;
cout.width(12);
cout << 4.56 << endl;
cout.width(8);
cout << "xyz" << endl;
cout.width(6);
cout << 12 << endl;
Këto katër urdhëresa për dalje japin në dalje:
4.560000
4.560000
xyz
12
Të theksojmë se secila vlerë është shtyp brenda gjërësisë së përcaktuar. Ose urdhëresat:
Bazat e gjuhës programuese C++ S. Bekteshi 17

cout.width(10);
cout << 123 << endl;
cout.width(10);
cout << 12345 << endl;
cout.width(10);
cout << 1234567 << endl;
Këto tri urdhëresa për dalje japin në dalje:
123
12345
1234567

Përdorimi i karaktereve të modifikimit të gjërësisë (width) është në programin prg.22.

Opsionet e hyrjes - cin vepron ngjashëm me tastaturën dhe e kombinuar me operatorin >> , cin
pauzon programin dhe pret nga shfrytëzuesi ti jep të dhënat nga tastatura. Me një cin, mund të
mirret një ose më shumë vlera (ngjashëm me cout me të cilin mund të paraqiten një ose më shumë
vlera), ku çdo vlerë në cin ndahet me nga një operator >> .

Shembull. Urdhëresa vijuese merr inputet nga shfrytëzuesi dhe i vendos në ndryshoren Rezultati:
cin >> Rezultati; // Mundëson shfrytëzuesin të shtyp vlera në Rezultati

Duhet theksuar se marrja e vlerave të shumëfishta bëhet me shtypjen e blank karakterit (çdo
hapësirë, butoni tab ose butoni enter).

Shembull: Për urdhëresën:


cin >> a >> b >> c; // I mer tri vlera nga tastatura
Shfrytëzuesi i shtyp tri vlera duke e lën nga një hapësirë mes tyre:
579
Ose shfrytëzuesi mund të shtyp butonin tab pas çdo vlere:
5 7 9
Ose shfrytëzuesi mund të shtyp butonin enter pas çdo vlere:
5
7
9
Në të gjitha rastet programi do ta ruan 5 në a, 7 në b, dhe 9 në c.
Mirëpo gabim është të shtypen numrat me presje si në formën
5, 7, 9
sepse programi C++ nuk e konsideron presjen si blank karakter. Preferohet që para çdo cin,me një
udhëzim të saktë se çfarë vlera dihet të jenë në hyrje si:
cout << "Ju lutem shtypni tre numra. Ndani që të tre" << endl;
cout << "vlerat me nga një hapësirë";
cin >> a >> b >> c;
ose cout << "Sa është vlera e parë (JU lutem pa presje dhjetore "<< endl;

Marrja e rreshtit të të dhënave - Nëse duhet të marrim një rresht nga hyrja atëhere përdoret
funksioni getline(). Ky funksion përdoret kur dëshirojmë ti fusim një string të të dhënave në vargun
e karaktereve. Përderisa cin e ndal leximin e të dhënave nga hyrja kur të mbërrin hapësira e parë,
getline() mbaron vetëm kur shfrytëzuesi e shtyp enter.
Bazat e gjuhës programuese C++ S. Bekteshi 18

Shembull: Ekzistojnë disa forma të getline(), por ajo që përdoret më së shpeshti e ka formën:
cin.getline(vargkarak, num);
ku vargkarak është çfardo vargu i karaktereve më parë i definuar që mban stringun hyrës. num është
numri maksimal i karaktereve që duhet të lexohen me getline(). cin. Nuk është pjesë e emrit
getline(). Më saktë, në këtë mënyrë objekti cin e merr rreshtin nga tastatura.

getline() gjithëmonë e përfundon leximin e të hyrave nga shfrytëzuesi kur numri maksimal i
karaktereve të plotësohet. getline() gjithashtu e rezervon për zeron që nevoitet për përfundimin e
stringut. Prandaj, getline() lejon që shfrytëzuesi të shtyp saktë numrin maksimal të karaktereve (
karakteri për rreshtin e ri kurrë nuk ruhet brenda stringut.) prg.23.

1. // Prg.23. Përdorimi i getline()


2. #include <iostream.h>
3. void main()
4. {
5. char qyteti[15];
6. cout << "Prej nga jeni? ";
7. cin.getline(qyteti, 15);
8. cout << "Ju jeni nga " << qyteti << endl;
9. return;
10. }
Daljat: Prej nga jeni? Mitrovicë - Kosovë
Ju jeni nga Mitrovicë - Kosovë

Me getline() mirret stringu nga shfrytëzuesi. cin pa getline() e merr vetëm një fjalë për një
herë prg.24

1:// Prg.24 Marrja e çmimit dhe artikullit


2: #include <iostream.h>
3:
4: void main()
5: {
6:
7: // Definimi i dy ndryshoreve
8: float cmimi;
9: char artikulli[25];
10:
11: cout << "Cili eshte artikulli? ";
12: cin.getline(artikulli, 25);
13:
14: cout << "Sa ëdhtë cmimi i artikullit? ";
15: cin >> cmimi;
16:
17: cout << endl << endl "Përshkrimi:" << endl
18: cout << " Artikulli: " << artikulli;
19:
20: cout.precision(2);
21: cout.setf(ios::fixed);
22: cout.setf(ios::showpoint);
23: cout << " Cmimi: " << cmimi << endl
Bazat e gjuhës programuese C++ S. Bekteshi 19

24: return;
25: }

Dalja:
Cili eshte artikulli? Libri Fizika
Sa ëdhtë cmimi i artikullit? 3.44
Përshkrimi:
Artikulli: Libri Fizika
Cmimi: 3.44

Analizë: Në rreshtin 9 është definuar vargu prej 25 karaktereve, dhe getline() në rreshtin 12 i merr
vlerat e vargut nga shfrytëzuesit. Pasi të shtypet çmimi në rreshtin 15, të dhënat shtypen përsëri në
rreshtin 17 deri 23.
Rreshtat 20, 21, dhe 22 sigurojnë që as më shumë e as më pak se dy decimale të shtypen për
çmimin. Pa këta manipulatorë H/D çmimi do të shtypej me gjashtë decimale.
Bazat e gjuhës programuese C++ S. Bekteshi 20

3. Tipet themelore të të dhënave

Konstantet dhe ndryshoret janë objekte me të cilat manipulon programi. Identifikatorët


përdoren për dhënjen e emrave konstanteve dhe ndryshoreve. Tipin e ndryshores e përcakton tipi i
vlerës ose i të dhënës e cila mund t’i jipet ndryshores si dhe tërësia e operatorëve të cilët mund të
zbatohen në ato vlera dhe madhësia e hapësirës së memories që nevojitet për vendosjen e vlerave të
ndryshores. Tipet themelore të të dhënave janë: int, float, double dhe char (Tabela.4).

Tabela 2. Tipet themelore të të dhënave

Tipi i të dhënave Përshkrimi i tipit të të dhënave


char Karakter
unsigned char Unsigned karakter
signed char Signed karakter (njejtë si char)
int Integer (numër i plotë)
unsigned int Unsigned integer
signed int Signed integer (njejtë si int)
short int Short integer
unsigned short int Unsigned short integer
signed short int Signed short integer (njejtë si short int)
long Long integer
long int Long integer (njejtë si long)
signed long int Signed long integer (njejtë si long int)
unsigned long int Unsigned long integer
float Numër real (me presje dhjetore)
double Double numër real (me presje dhjetore)
long double Long double numër real (me presje dhjetore)

Ndryshoret dhe komstantet

Një ndryshore është një lokacion në memorjen e kompjuterit në të cilin mund të ruhet një
vlerë dhe prej të cilit më vonë mund të mirret përsëri ajo vlerë. Kur të definohet një ndryshore në
C++ në këtë rast i tregohet kompajllerit se e çfarë lloji është ndryshorja: një integer (numër i ploë),
një karakter e kështu me radhë. Njëherit i tregohet kompajllerit se sa vend të rezervohet në memorje
dhe çfarë lloji të vlerës ruhet në ndryshore.
Krijimi ose definimi i një ndryshoreje bëhet duke e shkruar tipin, lihet një ose më shumë
vende të zbrazëta pastaj emri (identifikatori) i ndryshores dhe në fund vie pikëpresja.
tipi emri_dryshores;
Bazat e gjuhës programuese C++ S. Bekteshi 21

Në çdo kompjuter, çdo ndryshore zë vend të caktuar në memorje. Kjo dmth se psh një
integer në një kompjuter mund të jetë dy bajt kurse në tjetrin katër bajt por vlera e tij do të mbetet
gjithnjë e njejtë në secilin kompjuter. (Tabela 1.)

Tabela 2. Tipet e ndryshoreve.

Tipi Madhësia Vlera


unsigned short int 2 bajt 0 deri 65,535
short int 2 bajt -32,768 deri 32,767
unsigned long int 4 bajt 0 deri 4,294,967,295
long int 4 bajt -2,147,483,648 deri 2,147,483,647
int (16 bit) 2 bajt -32,768 deri 32,767
int (32 bit) 4 bajt -2,147,483,648 deri 2,147,483,647
unsigned int (16 bit) 2 bajt 0 deri 65,535
unsigned int (32 bit) 2 bajt 0 deri 4,294,967,295
char 1 bajt 256 vlera të karaktereve
float 4 bajt 1.2e-38 deri 3.4e38
double 8 bajt 2.2e-308 deri 1.8e308

Vërejtje: Madhësitë e ndryshoreve mund të jenë të ndryshme nga këto që janë paraqitur në
tabelën e mësipërme që varet nga kompjuteri dhe kompajlleri që ju e përdorni.

Shembull:
E dhëna Numri i bajtëve
që kërkohen
Shkronja x 1
Numri 800 2
Numri 123.123 4
Fjalia Te mesojme C++ 15
Një faqe e shtypur Afërsisht 3,000

Konstantet njësoj si edhe ndryshoret janë lokacione të memorjes për ruajtjen e të dhënave.
Dallimi me ndryshoret siç tregon edhe vet emri është se janë konstante dnth nuk ndryshohen. Posa
të krijohen atyre duhet t’iu jipet vlera dhe ato vlera nuk mund të ndryshohen.
Kemi dy lloje të konstanteve: literal dhe simbolik.
Krijimi ose definimi i një konstanteje literal bëhet duke e shkruar tipin, lihet një ose më
shumë vende të zbrazëta pastaj emërtimi (identifikatori) i konstantes që shoqërohet nga shenja e
barazimit pas së ciës vjen vlera e konstantës dhe në fund vie pikëpresja.
tipi emrindryshores = vlera;
Konstanta simbolike është konstanta që paraqitet me një emër (simbol).

Shembull: Konstantet literale


int numri = 20;
float pi = 3.14159;
Bazat e gjuhës programuese C++ S. Bekteshi 22

Konstantet simbolike: Nëse më parë në program është definuar konstanta simbolike me


emrin PI me vlerë 3.14159 atëhere mund të shkruhet:
Perimetri_rrethi = PI * (2 * rrezja);
Siperfaqja = PI * (rrezja)*(rrezja);
Në mënyrë të qartë shihet përparsia e përdorimit të konstanteve simbolike.

C++ i ka dy metoda për definimin e konstanteve simbolike duke i përdor fjalët e rezervuara
#define dhe const.

Tipi int

Të dhënat e tipit int janë vlerat e numrave të plotë. Në këtë kategori të të dhënave marrin
pjesë: konstantet, ndryshoret, shprehjet dhe funksionet. Në vazhdim do të japim rregullat për
shkruarjen dhe deklarimin e konstanteve dhe ndryshoreve që marrin vlera të numrave të plotë.

Deklarimi i ndryshoreve të tipit int

Duke u bazuar në atë që thamë më lartë, deklarimi i një ndryshoreje të tipit int bëhet duke e
shkruar tipin (int në këtë rast), lihet një ose më shumë vende të zbrazëta pastaj emri i ndryshores
dhe në fund vie pikëpresja.
int emri_ndryshores;
Për vënjen e emrave të ndryshoreve vlejnë të njejtat rregulla si për identifikatorët.

Shembull: Deklarimi i disa ndryshoreve të tipit int:


int emristudenti; - me emrin e ndryshores emristudenti
int x, y, rezultatit; - me emrin e ndryshoreve x, y, rezultatii

Nëse duhet ti deklarojmë dy ose më shumë (tri në rastin tonë) ndryshore atëhere:
int emri_ndryshores1;
int emri_ndryshores2;
int emri_ndryshores3;
ose në formën:
int emri_ndryshores1, emri_ndryshores2, emri_ndryshores3;

Dhënja e vlerave ndryshoreve (inicializimi)

Kur të deklarohet një ndryshore i jipen instruksione kompajllerit të rezervoj hapësirë të


memorjes për ndryshore. Megjithate, vlera e ruajtur në atë hapësirë – vlera e ndryshores—nuk është
definuar. Para se të përdoret ndryshorja ajo duhet të inicializohet me vlerën e njohur. Dhënja e
vlerave ndryshoreve respektivisht inicializimi bëhet me operatorin (=) e dhënjes së vlerave.

Shembull: Inicializimi i ndryshores shpejtesia bëhet si vijon:


int shpejtesia; // Rezervon hapësirë për ruajtje për shpejtësia
shpejtesia = 0; // E ruan 0 në shpejtesia
ose më shkurt:
Bazat e gjuhës programuese C++ S. Bekteshi 23

shpejtesia = 0;
Duhet theksuar se “shpejtesia=0” nuk kuptohet si në formën algjebrike “shpejtesia e
barabartë me zero” por si “ jepja vlerën 0 ndryshores shpejtësia”. Kjo më mirë do të kuptohej sikur
të paramendoni në vend të shenjës së “barazimit” të ishte shigjeta me kahje në të majtë ( ←).
Inicializimi i ndryshores mund të bëhet edhe me rastin e deklarimit të saj. Në këtë rast pas
emrit të ndryshores vendoset shenja e barazimit e cila shoqërohet me vlerën fillestare që dëshirohet,
psh:
int x=0, y=5, z=0; - me vlerë fillestare 0 për x, 5 për y dhe 0 pë z.
int matja1=0, matja2, matja3=123; matja1 me vlerë 0, matja3 me vlerë 123 dhe matja e
dytë nuk është inicializuar.

Inicializimi është mjaft i ngjashëm me operacionin e dhënjes së vlerave. Dallimi themelor


është se inicializimi zë vend në momentin e formimit të ndryshores. Ky dallim tek numrat integer
është shumë i vogël. Më vonë kur ti mësojmë konstantet do të shohim se disa vlera duhet të
inicializohen sepse ato nuk mund të jipen.
Konstantet e tipit integer mund të shkruhen në tri notacione të ndryshme:
 Një konstantë që fillon me çfardo numri përveç 0 interpretohet si integer dekad (që është
sistemi standard i numrimit me bazë 10). Konstantet dekade mund të përmbajnë numrat nga
0 deri 9 me parashenjë plus ose minus. (Nëse mungon parashenja plus ose minus, konstanta
shqyrtohet si pozitive.)
 Një konstantë që fillon me numrin 0 interpretohet si integer oktal (sistemi i numrimit me
bazë -8). Konstantet oktale mund të përmbajnë numrat prej 0 deri në 7 me parashenjë plus
ose minus.
 Një konstantë që fillon me 0x ose 0X interpretohet si konstantë heksadecimale (sistemi i
numrimit me bazë -16). Konstantet heksadecimale mund të përmbajnë numrat nga 0 deri në
9, shkronjat nga A deri në F, dhe parashenjën plus ose minus.

Tipi signed, unsigned, short ose long int

Të gjitha tipit integer mund të jenë signed ose unsigned.Tipi signed int i
përmbanë ose numrat pozitiv ose numrat negativ. Unsigned int janë gjithnjë pozitive. Pasi
numri i bajtëve signed int dhe unsignet int, numri më i madh që mund të ruhet në
signed int është dy herë më i madh se numri më i madh që ruhet si unsigned int.Nëse
ndyshorjet integer nuk deklarohet me signed ose unsigned nënkuptohen se janë signed.
Varësisht se vlerat që iu japim ndryshoreve janë të vogla ose të mëdha përdoret short ose
long. Një integer unsigned short mund të përdorë numra prej 0 deri në 65 535. Gjysma e
numrave që paraqiten me signed short janë negativ kështu që unsigned short mund të
përfaqson numrat prej -32 768 deri 32 768. unsogned long mund të ruaj numrin deri
4,294,967,295. Nëse ju duhet të ruani numra edhe më të mëdhej duhet të përdoren float dhe
double mirëpo me këtë rast humb saktësia sepse vetëm 7 ose 19 numrat e parë janë me rëndësi në
shumicën e kompjuterëve, shifart tjera rrumbullaksohen.
Duhet theksuar se gjatë inicializimit, vlerat e ndryshoreve nuk guxojnë ti tejkalojnë rangun e
vlerave të cilat i përmbajnë sepse rezultatet do të jenë papritura.
Bazat e gjuhës programuese C++ S. Bekteshi 24

typedef

C++ mundëson që tipin e të dhënave ta shkruajmë në formë më të shkurtë duke e përdor


fjalën e rezervuar typedef.

Shembull: Më lartë theksuam se mund të kemi tip të të dhënave të formës:


unsigned short int Gjatesia =5;
Nëse e përdorim typedef:
typedef unsigned short int USHORT;
atëhere fjala USHORT e zëvendson plotësisht frazën unsigned long int kështu që është shumë më
praktike të përdoret në program shkurtesa e theksuar.

Duhet theksuar se përdorimi i fjalës së rezervuar typedef nuk krijon tip të ri të dhënave ( i
cili është i mundshëm në C++ dhe për të cilin do të shohim më vonë) por e krijon një sinonim për
frazën e cila gjendet pas saj prg.20.

1 // prg20 Demonstrimi i përdorimit të fjalës së rezervuar typedef


2
3 #include <iostream.h>
4
5 typedef unsigned short int USHORT; //Definimi i typedef
6
7 void main()
8 {
9 USHORT Gjeresia = 5;
10 USHORT Gjatesia;
11 Gjatesia = 10;
12 USHORT Siperfaqja = Gjeresia * Gjatesia;
13 cout << "Gjeresia:" << Gjeresia << "\n";
14 cout << "Gjatesia: " << Gjatesia << endl;
15 cout << "Siperfaqja: " << Siperfaqja <<endl;
16 }
Dalja: Gjeresia: 5
Gjatesia: 10
Siperfaqja: 50

Analizë: Në rreshtin 5, unsigned short int. është zëvendsuar me sinonimin USHORT duke
përdor fjalën e rezevuar typedef dhe USHORT është përdor pastaj çdokund në program në vend
të unsigned short int..

Tipi float dhe double

Numrat me presje dhjetore janë tip tjetër i të dhënave në C++. Numrat me presje dhjetore
gjithashtu quhen edhe numra realë. Numri me presje dhjetore përcaktohet me fjalën e rezervuar
float ose double. Ndryshoret e tipit float dhe double ruajnë vlerat e numrave realë respektivisht
numra me presje dhjetore. Duhet theksuar se numrat decimal shkruhen me pikë ( jo me presje)
dhjetore kështu që për hirë të praktikës do t’a përdorim shprehjen “presje dhjetore” edhepse
faktikisht është pikë dhjetore.
Bazat e gjuhës programuese C++ S. Bekteshi 25

Ngjashëm me numrat ineger, numrat me presje dhjetore kanë një rang të kufizuar.
Stamdardi ANSI kërkon që rangu të jetë së paku plus ose minus 1.0*1037. Natyrisht, një numër me
presje dhjetore paraqitet me 32 bite. Prandaj, një numër me presje dhjetore është me saktësi gjashtë
shifrore (ose vende decimale) në anën e djathtë të presjes dhjetore. Një numër me presje dhjetore
nëse nuk e ka sufiksin (float) është i tipit të nënkuptuar double. Dallimi ndërmjet tipit float dhe
double është në saktësinë e paraqitjes së numrave realë. Saktësia e paraqitjes së numrave real është
në numrin e shifrave mbas presjes dhjetore të cilat mund të ruhen në hapsirën e memorjes
Ndryshoret e deklaruara të tipit double, thënë vrazhdë, mund të ruajnë afër dy herë më shumë shifra
decimale se ndryshoret e tipit float. Numri i saktë i shifrave varet nga lloji i kompjuterit.
Sqarim: Në Pentium, ndryshoret e tipit float mund të ruajnë përafërsisht 7 shifra decimale, ndërsa
ato të tipit double rreth 15 shifra decimale.
Përkundër pjestimit të numrave integer ku rezultati është i cunguar dhe pjesa thyesore nuk
paraqitet, pjestimi i numrave me presje dhjetore jep numër tjetër me presje dhjetore. Pjestimi me
numër me presje dhjetore kryhet kur pjestuesi ose i pjestueshmi janë numra me presje dhjetore ose
njëri nga ata është numër me presje dhjetore.

Shembull: Nëse 571.2 / 10.0 jep numrin tjetër me presje dhjetore 57.12. E njejta gjë vlen edhe për
571.2 / 10 si dhe 5712 / 10.0.

Deklarimi i ndryshoreve me presje dhjetore

Forma e përgjithshme e deklarimit të ndryshoreve me presje dhjetore është si vijon:


float emri_ndryshores;
ose për tipin double:
double emri_ndryshores;
Ngjashëm me deklarimin e nmrave të plotë (integer), për deklarimin e dy ose më shumë
ndryshoreve me preje dhjetore përdoret formati:
float emri_ndryshores1;
float emri_ndryshores2;
float emri_ndryshores3;
ose në formën:
float emri_ndryshores1, emri_ndryshores2, emri_ndryshores3;
Nuk ka dallim ndërmjet konstanteve të tipit float dhe double. Përkthyesi i C++, të gjitha
konstantet me presje dhjetore i shqyrton si të tipit double; Të theksojmë se edhe numrat e plotë
nëse shkruhen me presje dhjetore (psh 10. ose 10.0 etj), kompajlleri e trajton si vlerë me saktësi të
dyfisht pra të tipit double. Çdo konstantë e shkruar pa presje nga kompajlleri shqyrtohet si numër
integer.

#define

Njëra prej metodave për definimin e konstanteve simbolike është nëpërmes direktives
preprocesorike #define e cila përdoret në mënyrën si vijon:
#define EMRIKONSTANTES literali
Bazat e gjuhës programuese C++ S. Bekteshi 26

Në këtë mënyrë krijohet konstanta me emrin EMRIKONSTANTES (për të cilin vlejnë të njejta
rregulla si për identifikatorë) me vlerën e literalit. Literali paraqet një konstantë literale të
përshkruara më parë. Duhet të theksojmë se #define nuk përfundon me pikëpresje (;).
Direktiva preprocesorike #define e udhëzon kompajllerin si vijon: ” Në kodin burimor
zëvendsoje EMRIKONSTANTES me literali”. Efekti është i njejtë sikur me dorë të bëheshin këto
zëvendsime në kodin burimor. Urdhëresa preprocesorike #define mund të vendoset kudo në kodin
burimor (zakonish në fillim të kodit para main) ndërsa efekti i saj është në pjesën e programit
burimor pas saj.
Zakonisht emrat e konstanteve simbolike shënohen me shkronja të mëdha në mënyrë që më
lehtë të dallohen nga emrat e ndryshoreve (të cilat zakonisht shkruhen me shkronja të vogla).

Shembull: #define PI 3.14159

const

Metoda tjetër për definimin e konstanteve simbolike është nëpërmes fjalës së rezervuar
const. const përdoret në çdo deklarim të ndryshoreve. Një ndryshore e deklaruar si const nuk mund
të ndryshohet gjatë ekzkekutimit të programit. Nëse një gjë e tillë provohet në program, kompajlleri
lajmëron për gabim.

Shembull: Fjala e rezervuar const përdoret si vijon:


const int count = 100;
const float pi = 3.14159;
Efekti i const është në të gjitha ndryshoret (rezultati,GabimiAbsolut) që
gjenden në një rrjesht.
const long = 12000000, float = 0.21;
Një ndryshore e deklaruar si const nuk mund të ndryshohet gjatë ekzekutimit të
programit. Nëse një gjë e tillë provohet në program, kompajlleri lajmëron për gabim
const int masa = 100;
masa = 200; //Nuk e kompajllon! Nuk mund ta ndryshoj ose ti jap vlerë tjetër
konstantës

Duhet theksuar se dallimi ndërmjet direktives preprocesorike #define dhe fjalës së rezervuar
const shihet qartë te treguesit dhe fushëveprimi i ndryshoreve për të cilat do të bëhet fjalë më vonë)

Notacioni shkencor

Konstantet e tipit int, float dhe double mund të paraqiten në notacionin e zakonshëm dhe atë
shkencor. Gjatë shkruarjes së tyre në notacionin e zakonshëm mund të mos shkruhen pjesë para dhe
pas presjes dhjetore. Në notacionin shkencor një numër mund të paraqitet me kombinimin e
mantisës e shoqëruar nga shkronja e ose E dhe eksponentit si vijon:
[mantisa]e[exponenti],
dhe
[mantisa]E[exponenti].
Bazat e gjuhës programuese C++ S. Bekteshi 27

Shembull: 5000 në notacionin shkencor mund të paraqitet si 5e3 (5*10 3), -300 si –3E2 (-3*102),
dhe 0.0025 si 2.5e-3 (2.5*10-3).

Në tab janë paraqitur rutinat themelore të gjuhës C++ të cilat i kryejnë llogaritjet dhe
konverzionet matematike

1. prg19.
2. #include <iostream.h>
3. #include <conio.h>
4. #include <math.h>
5. int main ()
6. {
7. int x=253, y=463;
8. double z=pow(x,2)-3*y ;
9. cout <<"Te zgjidhet shprehja:\n\n";
10. cout <<"pow(x,2)="<<pow(x,2)<<"\n\n";
11. cout <<"3*y="<<3*y<<"\n\n";
12. cout <<"Zgjidhje\n\n";
13. cout <<"z=pow(x,2)-3*y="<<z<<"\n\n";
14. getch ();
15. return 0;
16. }
Dalja: Te zgjidhet shprehja:\
Zgjidhje
z=pow(x,2)-3*y=

Tipi char

Ndryshoret dhe konstantet e tipit char ruajnë karakteret, Në deklarata të këtilla përdoret fjala
e rezervuar char. Ndryshoret e tipit karakter (tipi char) janë zakonisht 1 bajt që mjafton të mbaj 256
vlera. Tipi char mund të interpretohet si numër i vogël (0-256) ose si numër i grupit ASCII
(American Standard Code for Information Interchange).
Shumica e kompjuterëve dhe të gjithë PC shfrytëzojnë kodin standard ASCII (Amerikan
Standard Code for Information Interchange) në të cilin çdo karakter është i koduar me vlerën 8
bitëshe që jep mundësinë e kodimit të 256 karaktereve të ndryshme

Sqarim: Kompjuterët nuk dijnë për shkronjat, shenjat e pikësimit ose për fjalitë. Krejt çka kuptojnë
ata janë numrat. Në të vërtetë ata dijnë sa ka apo nuk ka sasi të mjaftueshme të elektricitetit në
lidhje të caktuara të përquesve. Kjo paraqitet me 1, nëse ka dhe me 0 nëse nuk ka. Me grupimin e
njësheve dhe zerove kompjuteri është në gjendje të gjeneroj modele të cilat mund të interpretohen si
numra dhe këta me radhë mund të paraqiten si dhkronja ose shenja të pikësimit.
Në kodin ASCII, shkronja “a” ka vlerën 97. të gjitha shkronjat e vogla dhe të mëdha, të
gjithë numrat dhe të gjitha shenjat e piksimit kanë vlerat në mes 1 dhe 128. 128 shenjat dhe
simbolet tjera janë të rezervuara për përdorim të prodhuesve të kompjuterit

Kodi komplet ASCII është dhënë në shtesën. Në diskutimet e mëtejme do të përdorim vetëm kodin
ASCII.
Pasi karakteret janë të koduar me numra të plotë dhe mund të shqyrtohen si vlera të “vogla “
të plota dhe mund të definohet sistemi në mes të tyre .Prg.21. Vlera kodike e ”A” është më e vogël
Bazat e gjuhës programuese C++ S. Bekteshi 28

se vlera kodike e ”B” dhe mund të themi se “A” është më e vogël ss “B”. Ky sistemim quhet
sistemim leksigrafik dhe mundson sortimin e karaktereve, fjalëve dhe rreshtave .

1 Prg.21 Shtypja e shkronjave sipas numrave


2 #include <iostream.h>
3 int main()
4 {
5 for (int i = 32; i<128; i++)
6 cout << (char) i;
7 return 0;
8 }
Dalja: !"#$%G'()*+,./0123456789:;<>?@ABCDEFGHIJKLMNOP
_QRSTUVWXYZ[\]^'abcdefghijklmnopqrstuvwxyz

Ndryshoret e tipit char

Ndryshorja e cila mund të paraqes karaktere të ndryshme quhet ndryshore e tipit karakter
ose shkurt ndryshore karakter. Forma e përgjithshme e deklarimit të ndryshores karakter është:
char emri_ndryshores;
ku emri_ndryshores është identifikatori dmth vendi ku vendoset emri i ndryshores.

Shembull: Deklarimi i ndryshoreve ca, cb dhe iniciali:


char ca, cb, iniciali ;
Pjesa vijuese e programit i deklaron tri ndryshore dhe pastaj iu jep tri iniciale:
char Ipari, Imesmi, Ifundit;
Ipari = 'S';
Imesmi = 'T';
Ifundit = 'U';

Deklarimi i dy ose më shumë ndryshoreve karakter bëhet në këtë mënyrë:


char emri_ndryshores1;
char emri_ndryshores2;
char emri_ndryshores3;
ose në këtë mënyrë:
char emri_ndryshores1, emri_ndryshores2, emri_ndryshores3;

Konstantet e tipit char

Një karakter i kufizuar me thojza të njëfishta (‘) quhet konstante e tipi karakter ose shkurt
konstant karakter . Psh “a”, “A”, “b”, “B” janë të gjitha konstante karaktere që kanë vlerat e tyre
unike në grupin e karaktereve ASCII.. (çdo karakter i vetëm kufizohet me thojza të njëfishta.
Thojzat e dyfishta në gjuhën C++ përdoren për të paraqitur stringun e karaktereve i cili ka kuptim
krejt tjetër). Deklarimi i konstantes karakter bëhet në formën:
char emri_konstantes =’karakteri’;

Shembull: Konstantet e tipit char fitohen me vendosjen e karakterit në mes të thojzave të njëfishta
char ca =’A’, cb=’B’, iniciali=’S’ ;
Bazat e gjuhës programuese C++ S. Bekteshi 29

ose: char Viti =’I’;

Nga grupi i karaktereve ASCII mund të gjendet vlera (dekade) unike numerike e `A', `a',
`B', dhe `b' është 65, 97, 66, dhe 98, përkatsisht. Prandaj për ndryshoren karakter të dhënë x
deklaratat e poshtë shënuara janë ekuivalente
:x = `A';
x = 65;
si dhe deklaratat vijuese:
x = `a';
x = 97;

Karakteret e kalimit (escape characters)

Keni vërejtur edhe në programet e mëparshme së në vargjet konverzive të funksioneve cout


dhe cin shfrytëzojmë karakterin \n i cili paraqet një karakter edhe pse është i shënuar me “\”dhe “n”.
Karakteri kundërslash (\) ka kuptim të posaqëm në gjuhën C++ sepse disa karaktereve ia ndrron
kuptimin e tyre të zakonshëm dhe shërben për fitimin e escape karaktereve të cilat mundsojnë
paraqitjen e karaktereve që nuk janë grafike Psh rreshti i ri nuk mund të futet nga tastaura por
vetëm me ndihmën e escape karakterit \n ose nëse funksioni cout dërgohet karakteri “\b” atëhere
kursor i terminalit kthehet për një vend mbrapa, karakteri ”\” është vazhdim i rreshtit vijues .
Karakteri kundërslash së bashku me numrat oktal dhe heksadecimal përdoren për të paraqitur
simbolet ASCII ose kodin e kontrollit që i përgjigjet asaj vlere, psh “03” për Ctrl+C ose “cc3F” për
shenjën e pikëpyetjes. Karakteret e tilla quhen karaktere të kalimit (escape) (Tabela.3).
Forma \nnn mundson që në vargun e karaktereve të vendosen çfardo karaktere; ku nnn është
numri trefishor maksimal i plotë oktal dhe shënon paraqitjen kodike të karakterit. Në këtë mënyrë
është mundsuar që karakteret të cilat nuk mund ti shtypim me tastaturë ti fusim në vargun e
karaktereve .

Tabela 3. Karakteret e kalimit (escape).

Sekuenca Vlera Funksioni

\a 0x07 BEL Zilja


\b 0x08 BS Backspace, e çvendos kursorin për një karakter në të majtë.
\f 0x0C FF Formfeed, shkon në fillim të faqes së re.
\n 0x0A LF Rreshti i ri (linefeed)
\r 0x0D CR The return character, kthehet në fillim të rreshtit në vazhdim.
\t 0x09 HT Tab (horizontal) shkon për në tabin e vijues.
\v 0x0B VT Tab vertikal
\\ 0x5c \ Vija kundër e pjerrtë (backslash)
\' 0x27 ' Thojza e njëfisht (apostrofi)
\" 0x22 " Thojza e dyfisht
\? 0x3F ? Shenja e pikëpyetjes
\O cilido O=një string deri në tre shifra oktale
\xH cilido H=një string i shifrave hex
\XH cilido H=një string i shifrave hex
Bazat e gjuhës programuese C++ S. Bekteshi 30

Operatori cast

Operatori cast i konverton të dhënat nga një tip në tjetrin. Operatori cast shkruhet në atë
mënyrë që para tipit të të dhënave që dëshirojmë ta konvertojmë futet nën kllapa tipi i të dhënave në
të cilin dëshirojmë ta ndryshojmë si: (char), (int), (float) dhe (double). Për konvertimin e vlerave të
tipit të të dhënave në tjetër tip të të dhënave operatori cast vendoset mu para vlerës (ndryshores,
shprehjes, literalit).

Shembull: Konvertimi nga tipi float psh në integer bëhet ashtu që operatori cast integer
vendoset mu para ndryshores të tipit float.
int i = 8;
int rezultati;
float f = 6.9;
resultati = i * (int)f; // Konverton tipin e f para shumëzimit
f bëhet integer 6. Pa operatorin cast 8.0 shumëzohet me 6.9 dhe fitohet rezultati 55.2 para se të ruhet
55 në ndryshoren integer. Me operatorin cast 8.0 shumëzohet me 6 dhe fitohet 48 dhe 48 ruhet në
ndryshoren rezultati

Me operatorin cast lehtë mund të bëhet pjestimi me integer që jep rezultat me presje dhjetore

Shembull: Të shqyrtojmë edhe njëherë problemin pjestimit me integer që jep rezultat me numër të
plotë edhepse duhet me presje dhjetore. Për të fituar pjestim real përdoret operatori cast:
int koha,ngjarjet;
float mesatare;
mesatare = (float)koha / ngjarjet;
Tani C++ jep pjestim me numër me presje dhjetore.

Operatori cast mund të përdoret edhe për tërë një shprehje

Shembull: Operatori cast mund të përdoret edhe për tërë shprehjen:


rez = a + b * (long int)(e / y * 2);
Në këtë urdhëresë së dhënjes ës vlerave C++ e llogaritë rezultatin e e / y * 2 e pastaj e konverton
rezultatin e fituar në long integer.

Operatori cast nuk e ndryshon vlerat e tipit të të dhënave përgjithmonë. Vlera ndryshohet
për lokacionin e vetëm të operatorit cast.
Dizajnerët e C++ kanë dëshiruar që C++ të bazohet në gjihën C. Në C++, operatori cast
shkruhet në formën e notacionit të funksioneve. Në vend që të futet tipi i të dhënave nën kllapa, në
kllapa futet vlera që duhet të konvertohet

Shembull: Në C++, operatori cast shkruhet në formën e notacionit të funksioneve. Në vend që të


futet tipi i të dhënave nën kllapa, në kllapa futet vlera që duhet të konvertohet. Prandaj urdhëresat:
rezultati = i * (int)f; // Konverton f para shumëzimit
rezultati = (float)i * f; // C++ së pari e konverton i në float
x = a + b * (long int)(e / y * 2);
mund të shkruhen në formën:
rezultati = i * int; // Konverton f para shumëzimit
rezultzti = float(i * f); // C++ së pari e konverton i në float
x = a + b * long int(e / y * 2);
Ky notacion i C++ është ndoshta më i përshtatshëm
Bazat e gjuhës programuese C++ S. Bekteshi 31

4. Kontrollimi i rrjedhjes së programit

Në të gjitha programet e deritanishme deklaratat janë ekzekutaar një herë dhe vetëm një herë
sipas radhës së paraqittjes në program. Programet e këtilla janë tepër të thjeshtë sepse nuk
përmbajnë struktura logjike kontrolluese siç janë testet për përcaktimin së një kusht i caktuar a
është plotësuar duke përsëritur ekzekutimin e grupit të deklaratave ose pjesa e seleketuar r një grupi
të deklaratave nga disa të mundshme. Shumë programe në interes praktik në mënyrë intenzive i
shfrytëzojnë mundësitë e tilla.

Operatorët

Një operator është një simbol që e udhëzon C++ të kryej disa operacione ose aksione në një
ose më shumë operandë. Operand quhet çdo gjë në të cilën vepron operatori. Në C++ të gjithë
operandët janë shprehje. Operatorët ndahen në:
 Operatori i dhënjes së vlerave,
 Operatorët aritmetik.
 Operatorët krahasues (relacional)
 Operatorët logjik.

Operatori për dhënjen e vlerave

Operatori për dhënjen e vlerave (+) edhepse e ka shenjën e barazimit në aritmetikë, kuptimii
i tij është plotësisht tjetër. Deklarata për dhënjen e vlerave ka formën :
Operandi-majtë = Operandi-djathtë
dhe shkakton që Operandit-majtë i jipet (shënohet, shkruhet) vlera e Operandi-djathtë.
Në të vërtetë në këtë rast vlera e Operandi-djathtë i jipet (shënohet, shkruhet) në lokacionin e
memorjes të Operandi-majtë. Karakteri “=” paraqet operatorin e dhënjes së vlerave.

Shembull: Urdhëresa:
a = 5;
e shkruan vlerën e operatori-djathtë (5) në lokacionin e memorjes të ndryshores integer a (e cila
është operand-majtë në këtë rast). Ose urdhëresa:
b = a = 5;
i jep së pari vlerën 5 mdryshores integer a, dhe pastaj ndryshores integer b. Pas ekzekutimit të
urdhëresës edhe a edhe b e kanë vlerën 5.
Operatori i dhënjes së vlerave (=) asesi nuk dihet të ngatrrohet me operatorin e barazimit
(==) sepse kanë kuptime plotësisht të ndryshme. Urdhëresa e lartëshënuar nuk tregon se “a është e
barabartë me 5” por “vlera 5 i jipet a”

Operatori =i kërkon dy operandë (Operandi-majtë të cilës i jipet vlera dhe


Operandi-djathtë vlera e së cilës i jipet Operandi-majtë) prandaj është operator binar.
Urdhëresa për dhënjen e vlerave kthen të njejtën vlerë me të cilën është shënuar Operandi-
majtë.
Bazat e gjuhës programuese C++ S. Bekteshi 32

Operatorët dhe shprehjet aritmetike

Shprehjet janë kombinime të konstanteve, ndryshoreve, operatorëve dhe funksioneve.


Shprehjet aritmetike janë shprehjet të cilat përmbajnë operatorët aritmetik.
Operatorët aritmetik janë: “ + “, “-“, “ * “, “ / “ dhe “ % “. Operatorët * është operator i
shumëzimit ndërsa operatori % është operatori i modulit. Operatorët e theksuar iu përgjigjen
plotësisht operacioneve përkatëse aritmetike të mbledhjes, zbritjes, shumëzimit, pjestimit dhe
pjestimit sipas modulit. Operatorët aritmetik janë binarë përveç operatorit minus “ – “ i cili mund të
jetë edhe unar.
Operatori i pjestimit i zbatuar në vlerat e tipit int jep rezultate specifike; në të vërtetë
pjestimi i numrave të plotë e lëshon pjesën decimale (numrat mbas presjes dhjetore) ndërsa e mban
vetëm pjesën me numër të plotë.

Shembull: Si rezultat i pjestimit 1/3 fitohet 0, 2/3 fitohet 1, 16/3 fitohet 5 etj.

Operatori i pjestimit sipas modulit zakonisht zbatohet në numrat e plotë pozitiv. Si rezultat i
operatorit % fitohet mbetja pas pjestimit të numrave të plotë.

Shembull: Psh 9%2 jep 1, 10%3 jep 1, 26&9 jep 8 e kështu me radhë.

Në gjuhën C++ definohet prioriteti dhe asociativiteti i operatorëve aritmetikë.


Prioriteti i operatorëve përcakton radhën e ekzekutimit të operatorëve në shprehje kurse
Asocitiviteti i operatorëve përcakton radhën e ekzekutimit të operatorëve me prioritet të njejtë,
(Tabela 5)

Shembull: Në shprehjen:
a*b+c/d
operatorët * dhe / kanë priorite ndaj + kështu që së pari shumëzohet a me b pastaj pjestohet c me d e
pastaj mblidhen rezultatet e shumëzimit dhe pjestimit. Në shprehjen:
a*b/c
operatorët * dhe / kanë prioritet të njejtë kështu që tani në bazë të asociativitetit ( nga e majta në të
djathtë e këtyre operatorëve) së pari zbatohet shumëzimi e pastaj pjestimi.
Në shembullin vijues janë dhënë operatori i shumëzimit, modulit, mbledhjes dhe zbritjes:
Algjebrike z=pr%q+v/x -y
C++ z=p*r%q+v/q-y
6 1 2 4 3 5
Numrat e rrumbullaksuar tregojnë radhën e ekzekutimit të operatorëve. Operatori i
shumëzimit, modulit dhe pjestimit kryhen së pari pasi kamë prioritet të njejtë ndërsa asociativiteti
është nga e majta në të djathtë.

Me zbatimin e kllapave mund të ndërroj radha e ekzekutimit të operatorëve. Kllapat e kanë


prioritetin më të lartë. Në rastin e kllapave të një- dy- tre- fishta etj së pari ekzekutohen ato të
brendshmet.
Kombinimi i operatorit të dhënjes së vlerave (=) me operatorët aritmetik +, -, *, /, dhe %, jep
tipin e ri të operatorëve – operatorët aritmetik të dhënjes së vlerave: +=, -=, *=, /=, dhe %=,

Shembull: Në vazhdim janë paraqitur urdhëresa ekuivalente:


x += y; është ekuivalente me x = x + y;
x -= y; është ekuivalente me x = x - y;
Bazat e gjuhës programuese C++ S. Bekteshi 33

x *= y; është ekuivalente me x = x * y;
x /= y; është ekuivalente me x = x / y;
x %= y; është ekuivalente me x = x % y;
Të theksojmë se urdhëresa:
z = z * x + y; nuk është ekuivalente me urdhëresën z *= x + y;
sepse
z *= x + y është e njejtë me z = z * (x + y);

Operatori minus unar (-) përdoret për ndërrimin e parashenjes së ndryshores. Quhet unar
sepse i nevoitet vetëm një operand. Nuk duhet të ngatrrohet me operatorin e zbritjes (-) edhepse e
ka të njejtin simbol.

Operatorët e inkrementimit dhe dekrementimit

Operatorët e inkrementimit (++) dhe dekremntimit (- -) janë operatorë unarë me prioritet të


njejtë si dhe operatorët tjerë unarë dhe asociativitet nga e djathta në të majtë. Të dy operatorët
zbatohen vetëm në ndryshore dhe paraqiten në formën prefikse (para ndryshores) dhe postfikse (pas
ndryshores).
Operatori i inkrementimit ++ ndryshores p ia shton vlerën për 1 që dmth se :
p++ është ekuivalente me p=p+1
++p është ekuivalente me p=p+1
Operatori i dekrementimit ndryshores p ia zbret vlerën për 1 pra :
p - -_ është ekuivalente me p=p-1
- - p është ekuivalente me p=p-1
 Kur përdoret si prefiks, operatorët e inkrementimit dhe dekrementimite ndryshojnë
operandin e tyre para se të përdoret në shprehje.
 Kur përdoret si postfiks, operatorët e inkrementimit dhe dekrementimite ndryshojnë
operandin e tyre pasi që është përdorë në shprehje.
Në tabelën është dhënë prioriteti dhe asociativiteti komplet i operatorëve. Në këtë tabelë i
kemi edhe dy operatorë të rinj .
Operatori presje (,) ka prioritetin me të ultë ndaj të gjithë operatorëve tjerë. Ky është
operator binar ku shprehjet i shqyrton si operand. Në shprehjen: shprehja1, shprehja2 operatori
presje përcakton që shprehja1 të llogaritet e para e pastaj të llogaritet shprehja2 .Shprehja e
opratorit, si tërësi e ka vlerën 1 të tipit të operandit të djathtë:

Shembull: int i=0, j=2


Ndryshorja i është e deklaruar e tipit int atëhere edhe j është e tipit int me vlerë 2

Operatori sizeof si rezultat e jep vlerën e tipit int e cila është e barabartë me numrin e
bajtëve që nevojiten për ruajtjen e operandëve. .Forma e përgjithshme e këtij operatori është :

sizeof (tipi_te_dhënave)

Shembull: sizeof(int)
jep si rezultat numrin e bajtëve të cilat zauzima tipi int i të dhënave .
Bazat e gjuhës programuese C++ S. Bekteshi 34

Operatorët dhe shprehjet krahasuese (relacionale)

Operatorët krahasues (Tabela 6) bëjnë krahasimin në mes operandit të majtë dhe të djathtë.
Për të përcaktuar se kur janë të barabartë ose njëri më i madh se
tjetri. Operandët mund të jenë shprehje të çfardoshme. Të gjithë Tabela.6 Operatorët krahasues
operatorët krahasues janë binarë. Çdo urdhëresë krahasuese
rezulton në një (e saktë) ose zero (e pasaktë). < me i vogël se
Në C++, zeroja konsiderohet e pasaktë ndërsa të gjitha > me i madh se
<= me i vogël ose i barabartë
vlerat tjera konsiderohen të saktë edhepse e saktë zakonisht
>= me i madh ose i barabartë
paraqitet me një. Kështu nëse një shprehje është e pasaktë, ajo == i barabartë
është e barabartë me zero dhe nëse një shprehje është e barabartë != jo barabartë
me zero ajo është e pasaktë. Nëse një urdhëresë është e saktë kjo
dmth se ajo është e ndryshme nga zero dhe çdo urdhëresë e
ndryshme nga zero është e saktë

Shembull:
 Të shqyrtojme rastin a>b.
- nëse vlera e a është më e madhe se b, atëhere shprehja a>b është e saktë dhe shprehja a>b jep
vlerën 1 të tipit int,
- nëse a është më e vogël ose e barabartë se b shprehja a>b jep rezultatin zero të tipit int.
Dmth janë të mundshme dy vlera për shprehjen a>b, 1 të tipit int , nëse shprehja është e
saktë dhe 0 të tipit int nëse shprehja është e pasaktë .
 Disa shembuj për operatorët krahasues:
Barabartë == 100 == 50; Pasaktë
50 == 50; Saktë
jo e barabartë != 100 != 50; Saktë
50 != 50; Pasaktë
Më e madhe se > 100 > 50; Saktë
50 > 50; Pasaktë
Më e madhe ose e barabartë se >= 100 >= 50; Saktë
50 >= 50; Saktë
Më e vogël se < 100 < 50; Pasaktë
50 < 50; Pasaktë
Më e vogël ose e barabartë se <= 100 <= 50; Pasaktë
50 <= 50; Saktë
 Shprehja:
1 / 2 + 1 / 2 == 1
nga pikëpamja algjebrike është e saktë dhe supozohet të kthej vlerë. Shprehja megjithate kthen 0 që
dmth se shprehja e mësipërme nuk vlen. Kjo ndodh për shkak të pjestimit me integer sepse ½ jep 0
e jo 0.5.

Operatorët krahasues <, <=, >, >= kanë prioritet me të lartë ndaj == dhe !=. Operatorët ==
dhe != kanë prioritet të njejtë. Operatorët aritmetik janë me prioritet më të madh ndaj operatorëve
krahasues .
Pra operatorët krahasues (<, >, <=, >=) përdoren që të testojnë se shprehjet a janë të
barabarta apo jo të barabarta. Nëse deklarata është e saktë atëhere ajo kthen karakter jozero;
përndryshe ajo kthen të pasaktë (0)
Bazat e gjuhës programuese C++ S. Bekteshi 35

Operatorët dhe shprehjet logjike

Operatorët logjik i realizojnë operacionet logjike EDHE, OSE, JO (Tabela 7) Operatorët


logjik mundësojnë kombinimin e dy ose më shumë testimeve krahasuese në një urdhëresë të vetme
ose ndërrimin e vlerës që kthehet nga krahasimi. Tabela 7. Operatorët logjik
Operandët në shprehjen logjike duhet të jenë të tipit
skalar. Shp1 shp2 shp1&&shp 2 shp1|| shp1
Operatori ! (negacioni ) është operator unar 0 0 0 0
dhe mund të zbatohet në çfardo shprehje nëse shprehja 0 =0 0 1
=0 0 0 1
ka vlerën zero të cilit do tip dhe me zbatimin e =0 =0 1 1
operatorit të negacionit fitohet vlera 1 e tipit të njejtë
nëse shprehja ka vlerë jozero të çfardo tipi atëhere fitohet vlera zero e tipit int. Forma e
përgjithshme e negacionit logjik është:
! shprehja
Urdhëresa logjike JO bëhet e saktë nëse shprehja që testohet është e pasaktë dhe nëse
shprehja që testohet është e pasaktë vlera e testimit është e saktë. .

Shembull: Operatori JO - Shembuj të shkruar drejtë janë


! 10 !x !’x’
por jo me formën a!=b

Operatori i negacionit logjik dallon nga negacioni matematik.

Shembull: Nëse x është shprehje matematike atëhere për operatorin e negacionit matematik vlenë:
jo(jo x)=x
Nëse x ka vlerë jo zero të cilitdo tip atëhere për operatorin e negacionit logjik vlen :
!(!x)= 1
Në anën tjetër nëse shprehja x ka vlerën 0 atëhere për operatorin e negacionit logjik vlen;
!(!x)=0

Operatori ! ka prioritet dhe asociativitet (nga e djathta në të majtë) si dhe të gjithë operatorët
tjerë unarë .
Operatori && (logjik EDHE) jep si rezultat vlerën 1 ose 0 të tipi int. Operatorin && jep si
rezultat vlerën 1 nëse të dy operandët kanë vlerë jo zero. Në të kundërtën rezultati është 0.
Semantika e këtij operatori është dhënë në tabelën.
Një urdhëresë logjike EDHE i shqyrton dy shprehje dhe vetëm nëse të dy shprehjet janë të
sakta urdhëresa logjike Edhe është e saktë. Në shprehjet logjike, llogaritja ndërpritet. posa rezultati i
tërë shprehjes të mund të caktohet në bazë të llogaritjes së deriatëhershme psh në shprehjen :
shprehja1 && shprehja2.
shprehja2 nuk do të llogaritet nëse shprehja1 e ka vlerën zero.
Prioriteti i këtij operatori është më i ultë se ata unarë, aritmetik dhe krahasues kurse
asociativiteti i tij është nga e majta në të djathtë.

Shembull: Operatori EDHE - Kushti që studenti i vitit të dytë të kaloj klasën është që numri i
kredive të jetë më i madh ose i barabartë me 30.
Viti==2&&kredia>=30
Bazat e gjuhës programuese C++ S. Bekteshi 36

Kushti para operatorit EDHE logjik (Viti==2) ekzekutohet i pari sepse operatori == është me
prioritet se operatori &&. Pastaj ekzekutohet kushti pas operatorit EDHE logjik (kredia>=30) sepse
operatori >= është me prioritet se operatori &&.
Shprehja e mësipërme është e saktë nëse dhe vetëm nëse të dy kushtet janë të sakta (Viti==2
dhe kredia>=30). Çdo kombinim tjetër për shprehjen e mësipërme jep vlerë të pasaktë.
Duhet të theksojmë se ana e djathtë ekzekutohet vetëm nëse ana e majtë është e saktë.

Operatori || (logjik OSE) mund të jep poashtu dy vlera 0 ose 1. Ky operator jep si rezultat
vlerën zero nëse të dy operandët kanë vlerë zero. Në të kundërtën jep vlerën 1.: Një operator logjik
Ose evaluates dy shprehje. Nëse vetëm njëra prej tyre është e saktë shprehja shprehja është e saktë.
shprehja1 || shprehja2
shprehja2 nuk do të llogaritet nëse shprehja1 ka vlerën 0
Prioriteti i operatorit II është i njejtë me && dhe ka prioritet me të ultë se operatorët unarë,
aritmetik, dhe krahasues. Asociativiteti i tij është nga e majta në të djathtë.

Shembull: Operatori OSE - Nota me të cilën vlersohet studenti është: më e vogël se 11 ose më e
madhe se 4:
(Nota < 11 || Nota > 4)

Semantika e këtij operatori është dhënë në Tabelën.7

1. //prg.11
2.
3. #include <iostream.h>
4. #include <conio.h>
5.
6. main ()
7. {
8. int j=0, x, I=0, y=0;
9.
10. cout<<"Kuptimi i opratorit &&\n";
11. x=1&&(I=10);
12. cout<<"x= "<<x<<"\tdhe\tI= "<<I;
13.
14. cout<<"Kuptimi i opratorit II\n";
15. y=0.&&(j=100);
16. cout<<"\ny= "<<y<<"\tdhe\tj= "<<j;
17.
18. getch();
19. return 0;
20. }
Dalja:
Kuptimi i operatorit &&
x= 0 dhe j= 0
Kuptimi i operatorit II
y= 0 dhe j= 0
Bazat e gjuhës programuese C++ S. Bekteshi 37

Operatori i shprehjes së kushtëzuar

Operatori i shprehjes së kushtëzuar është operatori me i jashtëzakonshëm në gjuhën C++.


Deri më tani kemi mësuar për operatorët unarë ose binarë. Operatori i shprehjes së kushtëzuar është
operator ternar sepse i kërkon ttre operandë. Për paraqitjen e këtij operatori përdoren dy karaktere,
pikëpyetja “?” dhe dy pikat “:”. Operandi i parë është para pikëpyetjes, i dyti në mes të pikëpyetjes
dhe dy pikave, kurse i treti pas dy pikave. Forma e përgjithshme e këtij operatori është :
kushti ? shprehja 1 : shprehja2
Nëse kushti është i vërtetë ekzekutohet shprehja1 Nëse kushti s’është i vërtetë ekzekutohet
shprehja2

kushti është shprehje e çfardoshme, më së shpeshti shprehje krahasuese, i cili llogaritet i pari nëse
kushti është i saktë atëhere llogaritet shprehja1 dhe ky rezultat e definon vlerën e tërë shprehjes së
kushtëzuar. Në të kundërtën nëse kushti është jo i saktë atëhere llogaritet shprehja2 dhe ai rezultat e
përcakton vlerën e tërë shprehjes së kushtëzuar. Shprehja e kushtëzuar funksionon si urdhëresa if-
else për të cilën do të mësojmë më vonë.
Ky operator përdoret me së tepërmi që ndryshores t’i jipet njëra nga të dy vlerat e
mundshme. Në varshmëri nga kushti i caktuar. Të shqyrtojmë programin vijues prg22:

1. //prg.22
2.
3. #include <iostream.h>
4. #include <conio.h>
5.
6. main ( )
7. {
8. int ndrysh1, ndrysh2, minimum;
9.
10. cout<<"Vlera e ndryshores së parë: /";
11. cin >> ndrysh1;
12.
13. cout<<"Vlera e ndryshores së dytë:";
14. cin >> ndrysh2;
15.
16. minimum=(ndrysh1<ndrysh2)?ndrysh1:ndrysh2;
17. cout<<"\nVlera minimale eshte:%d"<<minimum;
18.
19. getch();
20.
21. return 0;
22. }
Dalja:
Vlera e ndryshores së parë 4
Vlera e ndryshores së dytë 3
Vlera minimale eshte 3

Analizë: Shprehja për gjetjen e vlerës më të vogël të dy ndryshoreve.e ka formën :


minimum =(ndrysh1<ndrysh2)?ndrysh1:ndrysh2
Bazat e gjuhës programuese C++ S. Bekteshi 38

Ndryshores minimum ia jep vlern ndrysh1 nëse kushti minimum është i saktë ose vlerën
ndrysh2 nëse kushti ndrysh1>=ndrysh2 i saktë. Kllapat shkruhen që të rritet lexueshmeria dhe nuk
janë të domosdoshme. Në mënyrë analoge kemi për max .:
minim=(ndrysh1<ndrysh 2)?ndrysh1:ndrysh2
Prioriteti i operatorit të shprehjes të kushtëzuar është me i ultë se i operatorit të dhënjes së
vlerave (=) dhe operatorit krahasues (<)
Nëse shprehja pas dy pikave është shprehje e kushtëzuar atëhere fitojmë:
S=(numri <0)?-1 : (numri=0)?-0:1)
(arrihet efekti i if-else-if për të cilin do të mësojmë më vonë )
Nëse vlera e ndyshores numri është më e vogël së zero ndryshores i jipet vlera 1 në të
kundërtën kryhet shprehja tjetër e kushtëzuar. Nëse në shprehjen e dytë të kushtëzuar ndryshorja
numri e ka vlerën zero ndryshorja e fiton vlerën 0. Në rastin kur vlera e ndryshores numri është më
e madhe së zero ndryshes e fiton vlerën 1. Kllapat nuk janë të nevojshme pasi asociativiteti i
operatorit të kushtëzimit është nga e djathta në të majtë, dmth shprehja e kushtëzuar :
u1? v1: u2? :v3
llogaritet si :
u1?v1:u2?v2:v3
Operatori i shprehjes së kushtëzuar trajtohet si çdo shprehje ose operator tjetër dhe për këtë
arsye ai mund të shkruhet çdokund ku mund të shkruhen edhe shprehjet dhe operatorët tjerë.

Përfundim:

 Operandët në shprehjen logjike duhet të jenë të tipit skalar.


 && EDHE logjike; e kthen të saktë vetëm nëse të dy shprehjet janë të ndryshme nga zero,
përndryshe e kthen të pasaktë. Nëse shprehja1 është e pasaktë shprehja2 nuk ekzekutohet.
 ! Negacioni logjik e kthen të saktë nëse e tërë shprehja është e ndryshme nga zero dhe
anasjelltas. Shprehja !E është ekuivalente me (0 == E).
 Operatorët aritmetik përdoren për kryerjen e llogaritjeve matematikore
 Shprehja unare me + dhe – shënon vlerën pozitive ose negative në shprehjen cast;
 + (mbledhja), - (zbritja), * (shumëzimi) dhe / (pjestimi) kryenë operacionet themelore
aritmetike në të gjitha tipet e të dhënave, integer dhe floating point.
 % (operatori i modulit) e kthen mbetjen e pjestimit të numrave të plotë (int) dhe nuk mund
të përdoret me numra me presje dhjetore.
 ++ (inkrementi) e rrit (shton) vlerën e shprehjes për një. Postinkrementi e rrit vlerën e
shprehjes për një pasi ajo të jetë ekzekutuar; përderisa preinkrementi e rrit për një para se të
ekzekutuar, -- (dekrementi) e zvoglon (zbret) vlerën e shprehjes për një. Postdekrementi e
zvoglon vlerën e shprehjes për një pasi ajo të jetë ekzekutuar; përderisa predekrementi e
zvoglon për një para se të ekzekutuar.
Bazat e gjuhës programuese C++ S. Bekteshi 39

5. Rrjedhja e programit dhe drejtimi i ekzekutimit

Të gjitha programet pa marr parasysh së a janë të thjeshta apo të komplikuara paraqesin një
rrjedhje të ekzekutimit të urdhëresave.

Strukturat e kontrollit

Kur urdhëresat në program ekzekutohen në radhë njëra pas tjetrës ashtu siç janë shkruar kemi të
bëjmë me ekzekutimin sekuencial. Urdhëresa të ndryshme të C++ i mundësojnë programuesit të
përcaktoj ekzekutimin e ndonjë urdhërese tjetër e cila mund të jetë edhe jashtë radhës. Kjo paraqet
transferin e kontrollës. Të gjitha programet mund të shkruhen në bazë të vetëm tri strukturave
kontrolluese:
- Struktura sekuenciale
- Struktura zgjedhëse dhe
- Struktura përsëritëse.
Struktura sekuenciale është e inkorporuar në C++. Kompjuteri i ekzekuton urdhëresat e C++ në
radhë njëra pas tjetrës ashtu siç janë shkruar përveç se nëse urdhërohet ndryshe.
Në C++ i kemi tri tipe të strukturave të zgjedhjes: if, if-else dhe switch. Struktura e zgjedhjes if
ose e kryen (e zgjedh një aksion nëse kushti është i saktë (true) ose e kalon e kalon një aksion nëse
kushti është i pasaktë (false). Struktura e zgjedhjes if-else e kryen një aksion nëse kushti është i
saktë ose kryen aksione tjera nëse kushti është i pasaktë. Struktura e zgjedhjes switch e kryen njërin
nga disa aksione varsisht nga vlera e shprehjes. Struktura e zgjedhjes if quhet strukturë zgjedhëse e
njëfishtë sepse ajo zgjedh ose e injoron (kalon) vetëm një aksion. Struktura e zgjedhjes if-else quhet
strukturë zgjedhëse e dyfishtë sepse ajo zgjedh në mes të dy aksioneve të ndryshme. Struktura e
zgjedhjes switch quhet strukturë zgjedhëse e shumëfishtë sepse ajo zgjedh aksionin që e kryen nga
shumë aksione tjera të ndryshme.
Në C++ i kemi tri tipe të strukturave të përsëritjes: while, do-while dhe for.
Shumë probleme të programimit zgjidhen me veprime të përsëritura në të njejtat të dhëna. Kjo
arrihet me dy mënyra : rekursion dhe iteracion. Iteracioni dmth kur e bëjmë të njejtën gjë prap dhe
prap. Metoda kryesore e iteracionit është cikli.

Struktura zgjedhëse if

Ekzekutimi sekuencial i urdhëresave të programit prishet me degëzimin përpara ose prapa


në bazë të vlerave të shprehjes drejtuese. Urdhëresat të cilat
Fillimi
e kryejnë degëzimin përpara quhen urdhëresa të zgjedhjes
(të sjelljes së vendimeve ). Urdhëresat e zgjedhjes e
zgjedhin një nga dy ose më tepër rrugëve të mundshme të
ekzekutimit të programit . Saktë
Kushti Urdhëresa
Urdhëresat e zgjedhjes shfrytëzohen në programe
për sjelljen e vendimeve. Urdhëresa themelore e zgjedhjes
është urdhëresa if. Forma e përgjithshme e urdhëresës if Pasaktë
është :
Fundi
if (Kushti )
Fig.4 Diagrami i rrjedhjes së
strukturës if
Bazat e gjuhës programuese C++ S. Bekteshi 40

urdhëresa
Kushti duhet të jetë nën kllapa. Paraqitja e rreshtit të dytë është konvencionale. vetëm sa për
të theksuar se urdhëresa është e nënshtruar. Në rrjedhjen e ekzekutimit të programit ndikon vlera
Kushti i cili duhet të jetë shprehje skalare. Të përkujtojmë së vetëm shprehjet skalare (aritmetike
ose treguesore) japin rezultate të cilat mund të krahasohen me zero. Kur përcaktohet vlera e kushtit
mund të fitohet vlera e barabartë ose ndryshme nga zero .Vlera zero si vlerë e kushtit është jo e
saktë logjike ndërsa vlera e ndryshme nga zero është e saktë logjike
Urdhëresa e nënshtruar nga urdhëresa e thjeshtë if do të ekzekutohet nëse kushti e ka vlerën
e saktë. Nëse kushti e ka vlerën e pasaktë, urdhëresa kapërcehet, kurse ekzekutimi i programit
vazhdon nga urdhëresat e tjera me radhë.
Diagrami i urdhëresës if është paraqitur në fig. 4. Ky diagram përmban simbolin e vendosjes
i cili përmban një shprehje në formë kushti i cili mund të jetë ose i saktë ose i pasaktë. Simboli i
vendosjes i ka dy vija të rrjedhjes të cilat dalin nga ai. Njëra tregon drejtimin që e merr kur kushti
është i saktë ndërsa tjetra kur kushti është i pasaktë. Vendimi mirret duke u bazuar në kushtet e
operatorëve relacional, të barazimit ose të çfardo kushti – nëse kushti merr vlerën zero ai trajtohet si
i pasaktë ndërsa nëse kushti merr vlerë të ndryshme nga zero ai trajtohet si i saktë.
Zbatimi i urdhëresës if është paraqit në kodin prg5.

1. // prg5
2. #include <iostream.h>
3. int main()
4. {
5. int num1, num2; // deklarata
6.
7. cout << "Shtypni dy numra: "; // kërkon
8. cin >> num1 >> num2; // ti shtypim dy numra
9. if ( num1 == num2 )
10. cout << "Numrat janë të barabartë." << endl;
11. if ( num1 > num2 )
12. cout << num1 << " është më i madh." << endl;
13. if ( num2 > num1 )
14. cout << num2 << " është më i madh." << endl;
15. return 0;
16. }

Struktura zgjedhëse if-else

Theksuam më parë se urdhëresa if e kryen një aksion vetëm në rastin kur shprehja drejtuese
është e saktë përndryshe aksioni is dropped. Urdhëresa if-else e lejon programuesin të përcaktojë se
cili nga aksionet do të kryhet në rastin kur shprehja drejtuese është e saktë dhe cili aksion do të
kryhet kur shprehja është e pasaktë. Sintaksa e urdhëresës if else është:
if (Kushti)
urdhëresa1;
else
urdhëresa2
Nëse vlera logjike e kushtit është e saktë ekzekutohet urdhëresa1 ndërsa kur kjo vlerë është
e pasaktë ekzekutohet urdhëresa2. Diagrami i rrjedhjes i urdhëresës if-else është paraqitur në fig. 5.
Bazat e gjuhës programuese C++ S. Bekteshi 41

Fillimi

Pasaktë Saktë
urdhëresa2 Kushti urdhëresa1

Fundi

Fig.5 Diagrami i rrjedhjes së strukturës if-else

Për ilustrim do të japim kodin i cili e kërkon numrin e satelitëve të Jupiterit dhe në bazë të numrit të
dhënë jipet lajmërimi se numri i dhënë është i saktë ose i pasaktë.
Urdhëresat e përfshira (nested) shërbejnë për testimin e rasteve të shumëfishta me vendosjen
e urdhëresave if-else brenda urdhëresave if-else. Përfshirja në degën e pasaktë është mjaftë e
shpeshtë në programet e C++. Ja si duket forma e përgjithshme :
if (shprehja1)
urdhëresa1;
else
if (shprehja2)
urdhëresa2;
else
urdhëresa3
…………..
kjo urdhëresë e drejtimit shumëkahësh mund të shprehet në formë më të qartë dhe më kompakte në
formën:
if (shprehja1)
urdhëresa1;
else if (shprehja2)
urdhëresa2;
else
urdhëresa3
…………..
Anëtari opcional është dega e cila nënkuptohet (angl. “default”) respektivisht dega në të
cilën shkohet nëse njëra ose asnjëra nga shprehjet drejtuese nuk jep vlerën e saktë. Nëse për atë rast
nuk është i paraparë asnjë aktivitet atëhere anëtari else është i panevojshëm.
Siç shihet nga fig.5 rrjedhja e programit shkon nëpër vargun e shprehjeve drejtuese. Nëse
njëra nga këto shprehje jep vlerën e saktë atëhere ekzekutohet urdhëresa përkatëse e saj dhe
programi vazhdon nga urdhëresa e cila është pas urdhëresës if.
Struktura zgjedhëse if e pret vetëm një urdhëresë në trupin e saj. Në rastin kur kemi më
shumë urdhëresa ato duhet të futen brenda kllapave të mëdha {}. Urdhëresat e tilla quhen urdhëresa
Bazat e gjuhës programuese C++ S. Bekteshi 42

të përbëra. Në shembullin e mëposhtëm është dhënë një shembull i urdhëresës së përbërë në pjesën
else:
if (shprehja1)
urdhëresa1;
else
{
urdhëresa2;
urdhëresa3
}
Në fund duhet theksuar se urdhëresa if-else është mjaft e ngjashme me operatorin e
shprehjes së kushtëzimit
Bazat e gjuhës programuese C++ S. Bekteshi 43

Formulimi i algoritmeve

Për të treguar zhvillimin e algoritmeve do të shqyrtojmë problemin për përcaktimin e numrit


mesatar të poenave të klasës në formën:
Një klasë me dhjetë student ka pasur testim. Për çdo student numri i poenave është prej 0
deri në 100. Të përcaktohet mesatarja poenave e kësaj klase për këtë test.
Numri mesatar i poenave të kësaj klase fitohet me shumën e poenave të saktë pjestue me
numrin e studentëve (10). Algoritmi për zgjedhjen e këtij problemi duhet ti pranoj poenat secilin
student, të llogaris mesataren dhe ti shtyp rezultatet.
Le ta përdorim pseudokodin për të treguar aksionet të cilat duhet të ekzekutohen dhe radhën
e aksioneve që duhet të ekzekutohen. Për ti futur të dhënat për çdo student do të përdorim
numruesin kontrollues të përsëritjes. Kjo teknikë e përdor ndryshoren e cila quhet numruesi që të
kontrolloj numrin e herëve që do të ekzekutohet grupi i urdhëresave. Në shembullin tonë përsëritja
ndërpritet kur numruesi kalon 10. pseudokodi e ka formën:
 Vendosim shumën në zero
 Vendosim numruesin e poenave në një
 Përderisa numruesi poenave të jetë më i vogël ose i barabartë me 10
 Të futen poenat për çdo student me radhë
 Të mblidhen poenat në shumë
 Ti shtohet një numruesit të poenave
 Të vendoset mesatarja e klasës ashtu që shuma pjestohet me 10
 Të shtypet mesatarja e klasës

Programi përkatës e ka formën:

1 // Programi për mesataren e klasës me numruesin kontrollues të përsëritjes


2
3 #include <iostream.h>
4
5 int main()
6 {
7 int shuma, // shuma e poenave
8 numruesiPoena, // numri i poenave
9 poeni, // poenat për çdo student
10 mesatarja; // mesatarja e poenave
11
12 // faza e inicializimit
13 shuma = 0; // shuma e pastër
14 numruesiPoena = 1; // përgaditja për cilël
15
16 // faza e përpunimit
17 while ( numruesiPoena <= 10 ) { // përsërit 10 herë
18 cout << "Shtypi poenat: "; // i kërkon për input
19 cin >> poeni; // input poenat
20 shuma = shuma + poeni; // shumës ia shton poenat
21 numriPoena = numriPoena + 1; // numruesi inkrementohet deri në 10
22 }
23
24 // faza e ndërprerjes
Bazat e gjuhës programuese C++ S. Bekteshi 44

25 mesatarja = shuma / 10;


26 cout << "Mesatarja e klasës është " << mesatarja << endl;
27
28 return 0; // tregon se programi ka përfunduar me sukses
29 }

Të theksojmë se llogaritja e mesatares në program jep vlerë të tipit int. Në të vërtetë shuma e
poenave psh 855 kur pjestohet me 10 jep 85.5 pra numër me presje dhjetore. Tregoni se si duhet të
veprojmë me numra me presje dhjetore (floating point numbers).
Bazat e gjuhës programuese C++ S. Bekteshi 45

Struktura përsëritëse (cikli) while

Në gjuhën C++ kemi edhe urdhëresa të cilat e kthejnë degëzimin prapa, që quhen urdhëresa
(cikle) të përsëritjes. Cikli while mundëson që ekzekutimi
të bartet prapa në ndonjë urdhëresë të mëparshme. Qëllimi Fillimi
i ciklit while është që të mundësoj ekzekutimin e trupit të
ciklit përderisa vlera në kusht të mbetet e saktë. Strukturat
përsëritëse i mundësojnë programuesit që të përcaktojnë
Saktë
një aksion i cili do të përsëritet përderisa kushti të mbetet i Kushti Urdhëresa
saktë.
Forma e përgjithshme e ciklit while është: Pasaktë
while (kushti)
Fundi
urdhëresa;
Fig.6. Diagrami i rrjedhjes së
Kushti i cili testohet në ciklin while mund të jetë
strukturës përsëritëse while
çfardo shprehje që vlen në C++. Përderisa kushti është i
saktë ciki while do të vazhdoj.

// Programi për mesataren e klasës me numruesin kontrollues të përsëritjes


2
3 #include <iostream.h>
4
5 int main()
6 {
7 int shuma, // shuma e poenave
8 numruesiPoena, // numri i poenave
9 poeni, // poenat për çdo student
10 mesatarja; // mesatarja e poenave
11
12 // faza e inicializimit
13 shuma = 0; // shuma e pastër
14 numruesiPoena = 1; // përgaditja për cilël
15
16 // faza e përpunimit
17 while ( numruesiPoena <= 10 ) { // përsërit 10 herë
18 cout << "Shtypi poenat: "; // i kërkon për input
19 cin >> poeni; // input poenat
20 shuma = shuma + poeni; // shumës ia shton poenat
21 numriPoena = numriPoena + 1; // numruesi inkrementohet deri në 10
22 }
23
24 // faza e ndërprerjes
25 mesatarja = shuma / 10;
26 cout << "Mesatarja e klasës është " << mesatarja << endl;
27
28 return 0; // tregon se programi ka përfunduar me sukses
29 }
Bazat e gjuhës programuese C++ S. Bekteshi 46

Shembull: Të shqyrtojmë pjesën e programit e cila ka për detyrë të fitoj numrin e parë pas 1000 që
fitohet me ngritjen në fuqi të 2. Të supozojmë se ndryshorja e tipit integer prodhimi është
inicializuar në 2. kur cikli while vijues përfundon do ta kemi rezultatin e dëshiruar
int prodhimi=2;
while (prodhimi<=1000)
prodhimi=2*prodhimi;
Kur fillon cikli while vlera e prodhimi është 2. Ndryshorja prodhimi shumëzohet me 2 në
mënyrë të përsëritur duke fituar vlerat 2, 4, 8, 16, 32, 64, 128, 256 dhe 1024. Kur prodhimi bëhet
1024 kushti i cikli while prodhimi<=1000 bëhet i pasaktë. Në këtë rast përsëritja ndërpritet dhe
prodhimi merr vlerën përfundimtare 1024. Ekzekutimi i programit vazhdon në urdhëresën e parë
pas ciklit while.

Urdhëresat që e përbëjnë strukturën while e formojnë trupin e while. Trupi i strukturës while
mund të jetë vetëm një urdhëresë ose një urdhëresë e përbërë. Në rastin kur kushti bëhet i pasaktë,
përsëritja ndërpritet dhe urdhëresa e parë pas strukturës while.
Diagrami i rrjedhjes (fig. 6) e ilustron rrjedhjen e kontrollës së strukturës while. Diagrami i
rrjedhjes në mënyrë të qartë e paraqet përsëritjen. Vija e rrjedhjes e cila del nga katrori kthehet
prapa në vendosje që testohet çdo herë nëpër cikël përderisa kushti të jetë i pasaktë kushti është i
pasaktë. kontrolla kalon në urdhëresën në vazhdim të programit.
Cikli while e verifikon kushtin në “maje” të ciklit (shiqo fig.8). kjo dmth se trupi i
urdhëresës nuk do të ekzekutohet nëse përcaktimi i vlerës së kushtit jep rezultatin zero. Nëse
përcaktimi i vlerës jep rezultat të ndryshëm nga zero, urdhëresa ekzekutohet.

Struktura përsëritëse do-while

Struktura përsëritëse do-while është e ngjashme me strukturën përsëritëse while. Në


strukturën while kushti për vazhdimin e ciklit testohet në fillim të ciklit para se të ekzekutohet trupi
i ciklit. Kushti te ky cikël gjendet në “fundin” e ciklit, siç është paraqitur në figurën.9. Struktura do-
while e teston kushtin për vazhdimin e ciklit pasi të Fillimi
ekzekutohet trupi i ciklit prandaj trupi i ciklit do të
ekzekutohet së paku një herë. Pra, ky cikël ka për qëllim që
urdhëresat që gjenden në trupin e ciklit të ekzekutohen
gjithësesi bile edhe në ato raste kur kushti merr vlerë të
pasaktë. Kur ekzekutimi i programit hyn në urdhëresën do aksioni
atëhere ekzekutohet urdhëresa nga trupi i ciklit dhe vetëm
atëhere përcaktohet vlera e kushtit.
Saktë
Forma e përgjithshme e ciklit do-while është: Kushti Urdhëresa
do
Pasaktë
urdhëresa
while (kushti); Fundi

Diagrami i rrjedhjes për strukturën do-while është Fig.7 Diagrami i rrjedhjes së


dhënë në fig. 7. Diagrami në mënyrë të qartë paraqet se strukturës do-while
kushti për vazhdimin e ciklit nuk ekzekutohet përderisa të
kryhet aksioni së paku një herë.
Kur të kryhet cikli do-while ekzekutimi kalon në urdhëresën e parë pas while. Të theksojmë
se përdorimi i kllapave nuk është i domosdoshëm nëse në trup është vetëm një urdhëresë. Kllapat
zakonisht përdoren për të ju larguar keqkuptimeve në mes të strukturave while dhe do-while.
Bazat e gjuhës programuese C++ S. Bekteshi 47

Shembull:
while (shprehja)
paraqet kreun e strukturës while. Struktura do-while pa kllapa rreth trupit me një urdhëresë duket:
do
urdhëresa
while (shprehja);
mund të keqkuptohet. Rreshti i fundit while (shprehja); mund të keqkuptohet si një strukturë while
me një urdhëresë të zbraztë. Kështu struktura do-while me një urdhëresë shkruhet duke i përdorë
kllapat në mënyrë që ti shmangemi keqkuptimeve.
do
{
urdhëresa
}
while (shprehja);

Ciklet e përfshira

Ciklet mund të jenë të përfshira (angl. nested) dmth kur një cikël gjendet në trupin e ciklit
tjetër. Në këtë rast njëri cikël mund ta kontrolloj ciklin tjetër duke e zmadhuar fuqinë e cikleve.
Ciklet e përfshira mundësojnë ekzekutimin e ciklit më shumë se
një herë (cikël i cikleve). Shembëll për ciklet e përfshira mund të
jetë odometri (matësi i kilometrave të automjetit) i cili është i
ngjashëm me pesë-gjashtë cikle të përfshira for secili prej të
cilëve mund të merr vlera prej 0 – 9. Me lëvizjen e automjetit
numri i parë në të djathtë i odometrit ndërrohet më së shpejti nga
0 – 9. Kur ciklet janë të përfshira, cikli i jashtëm ciklohet më a) b)
ngadal se cikli i brendshëm ashtu si numrat odometrit në të
Fig. 8 Kombinimet
djathtë ndryshojnë më shpejtë se ata të majtë. Cikli i jashtëm
a) e lejuara, b) të palejuara
ndryshon vetëm asi cikli i brendshëm plotësisht të përfundoj.
Nëse kemi disa cikle do-while atëhere lejohet që brenda një cikli do-while të gjenden një ose më
shumë cikle tjera do-while (fig. 8a). Nuk lejohet që ciklet do-while të nyjëzohen (fig.8b).
Bazat e gjuhës programuese C++ S. Bekteshi 48

n 1 2
 x
Llogaritja e vlerës së funksionit: y    2i  
i  3i 
Fillimi
// Programi Prg2_9
#include <iostream> x, n
#include <cmath>

int main() s=0


{
int n,i;
double x,s;
cout << "Vlerat hyrëse x dhe n: ";
cin >> x >> n;
s=0; 2
 x
i=2; s  s   2i  
 3
do
{ i=i+1
s=s+pow(2*i+x/3,2);
i=i+1; Po
} i≤(n+1)
while (i<=n+1);
cout << "Shuma s=" Jo
<< s y
<< "\n";

return 0; Fundi
}

Dalja:

Vlerat hyrëse x dhe n: 1 5

Shuma s=317.778
Bazat e gjuhës programuese C++ S. Bekteshi 49

i
x k
 23
Llogaritja e vlerës së funksionit: y   2  x   Fillimi
3 i  i

x, k
// Programi Prg2_9
#include <iostream>
#include <cmath> s=0

int main()
{ i=1
int k,i;
double x,s,y;
i
cout << "Vlerat hyrëse x dhe k: ";  23
cin >> x>> k; s  sx 
s=0;  i
i=1;
i=i+1
do
{ Po
s=s+pow(x+2./i,i/3.); i≤k
i=i+1; Jo
}
while (i<=k); x
y  2s
y=x/3+2*s; 3

cout << "Vlera e funksionit y=" << y<< "\n";


return 0; y
}
Fundi
Dalja:
Vlerat hyrëse x dhe k: 1 3
Vlera e funksionit y=9.72597
Bazat e gjuhës programuese C++ S. Bekteshi 50

 n 1
 2 x  3  j  2 x 2 për x  4.5
Llogaritja e vlerës së funksionit: y   j 1
 2
3x  2 x  1 për x  4.5

// Programi Prg2_13 Fillimi


#include <iostream>
#include <cmath>
x, n
int main()
{ Po Jo
int n,j; x≤4.5
double x,y,s;
cout << "Vlerat hyrëse n dhe x: "; s=0
cin >> n >> x;
if (x<=4.55)
{ j=1
s=0;
j=1;
s  s   j  2x 
2
do
{
s=s+pow(j+2*x,2);
j=j+1; j=j+1
}
while (j<=n+1); Po
y=2*x+3*s; j≤(n+1)
} Jo

else y  2 x  3s y  3x 2  2 x  1
y=3*pow(x,2)+2*x-1;
cout << "Vlera e funksionit y="<< y << "\n";
return 0; y
}
Dalja:
Vlerat hyrëse n dhe x: 3 3.5 Fundi
Vlera e funksionit y=1105
Bazat e gjuhës programuese C++ S. Bekteshi 51

Struktura përsëritëse for

Forma e përgjithshme e strukturës përsëritëse for është:


for (shprehja1; shprehja2; shprehja3)
ku:
- shprehja1 e inicializon ndryshoren e kontrollit të ciklit,
- shprehja2 është kushti për vazhdimin e ciklit dhe
- shprehja3 e inkrementon ndryshoren e kontrollit.
Shprehja1 (seksioni i inicializimit) në kreun e strukturës for e definon ndryshoren e
kontrollit (tipi i ndryshores së kontrollit theksohet para emrit të ndryshores), ndryshorja e kontrollit
mund të përdoret vetëm në trupin e strukturës for pra vlera e ndryshores së kontrollit është e
panjohur jashtë strukturës for. Ky përdorim i kufizuar i emrit të ndryshores së kontrollit quhet
fushëveprimi i ndryshores. Fushëveprimi i ndryshores e definon se ku mund të përdoret ndryshorja
në program. Më poshtë janë dhënë disa shembuj të përdorimit të ndryshores së kontrollit.

Shembull: Ja disa shembuj të përdorimit të ndryshores së kontrollit në ciklin for:


– Ndryshorja e kontrollit të ndryshoj nga 1 deri në 100 me inkrementim për 1
for (int i=1;i<=100; i++)
– Ndryshorja e kontrollit të ndryshoj nga 100 deri në 1 me dekrementim për 1
for (int i=100;i>=1; i--)
– Ndryshorja e kontrollit të ndryshoj nga 7 deri në 77 me inkrementim për nga 7
for (int i=7;i<=77; i+=7)
– Ndryshorja e kontrollit të ndryshoj nëpër sekuencën e vlerave 2,5, 8, 11, 14, 17, 20
for (int i=2;i<=20; i+=3)
– Ndryshorja e kontrollit të ndryshoj nëpër vlerat 99, 88, 77, 66, 55, 44, 33, 22, 11, 0
for (int i=99 ;i>=0; i-=10)

Nganjëherë shprehja1 dhe shprehja2 është listë e ndarë me presje. Presja siç është përdor në
këtë rast paraqet operatorin presje dhe garanton që shprehjet do të ekzekutohen nga e majta në të
djathtë me radjë. Operatori presje ka prioritetin më të ultë ndaj të gjithë operatorëve të C++. Vlera
dhe tipi i listës së shprehjeve të ndara me presje është vlera
dhe tipi i shprehjes e cila gjendet në pozitën më të djathtë Fillimi
ndaj të gjitha të tjerave. Përdorimi parësor i operatorit
presje në strukturën for është që të mundsoj inicializimin e
shumëfishtë të shprehjeve dhe/ose inkrementimin e shprehja1
shumfisht të shprehjeve. P.sh. kur kemi disa ndryshore të
kontrollit vetëm në një strukturë for të cilat duhet të
inicializohen dhe inkrementohen.
Tri shprehje në strukturën for janë opcionale. Nëse
Saktë
mungon shprehja2, C++ supozon se kushti i vazhdimit të Shprehja2 shprehja3
ciklit është i saktë kështu që krijohet një cikël infinit. Nëse
ndryshorja e kontrollit është inicializuar diku tjetër në Pasaktë
program ajo mund të mungoj në strukturën for. shprehja3
mund të mungoj nëse nuk ka nevojë për inkrementim ose Fundi
nëse është llogaritë nga urdhëresat në trupin e strukturës
for. Megjithate dy pikëpresje duhet të jenë në strukturën Fig.9 Diagrami i rrjedhjes së
for. strukturës for
Pjesa e inicializimit, kushtit për vazhdimin e ciklit dhe e inkrementimit/dekrementimit mund
të përmbajnë shprehje matematikore.
Bazat e gjuhës programuese C++ S. Bekteshi 52

Shembull: Nëse x=2 dhe y=10 dhe nëse x dhe y nuk modifikohen në trupin e strukturës for atëhere
deklarata:
for (int j=x\; j<=2*x*y; j+=y/x)
Është ekuivalente me:
for (int j=2; j<=80; j+=5)

Nëse kushti për vazhdimin e ciklit që në fillim është i pasaktë atëhere trupi i strukturës for
nuk ekzekutohet; ekzekutimi kalon në urdhëresën e parë pas strukturës for. Nëse kemi më shumë se
një urdhëresë në trupin e strukturës for, kllapat nevojiten që të definohet trupi i ciklit.
Diagrami i rrjedhjes i strukturës for (fig. 9) është i ngjashëm me ate të strukturës while fig.
6. Nga diagrami shihet qartë se inicializimi ndodh vetëm një herë ndërsa inkrementimi ndodh çdo
herë kur ekzekutohet trupi i urdhëresës. Diagrami i rrjedhjes për rastin e mësipërm është dhënë në
fig. 10

Shembulli. Në fig është paraqitur diagrami i rrjedhjes për deklaratën:


for ( numruesi=1; numruesi<=10; numruesi++)
cout<<numruesi<<end1;

Struktura përsëritëse for i shfrytëzon Fillimi


të gjitha detalet e numruesit kontrollues të përsëritjeve. Prandaj stru
I jep vlerën fillesta
re ndryshores së numruesi=1
kontrollit

E teston se nëse vlera e Saktë


fundit e ndryshores së numruesi<=1 cout<<numruesi numruesi++
kontrollit nuk ka arritë <<end1;
Inkrementimi
Pasaktë Trupi i ciklit. i ndryshores
Këtu mund të jenë së kontrollit
Mbarimi disa deklarata
Fig.10 Diagrami i rrjedhjes së strukturës for për rastin e dhënë

Programin… (nga while) e shënojmë me ndihmën e ciklit for.


for ( numruesi=1; numruesi<=10; numruesi++)
Programi operon si në vazhdim: Kur struktura for e fillon ekzekutimin ndryshorja numruesi
deklarohet dhe inicializohet në 1. Pastaj kërkohet kushti për vazhdimin e ciklit numruesi<=10. Pasi
vlera e numruesit është 1 kushti kënaqet kështu që trupi i urdhëresës e shtyp vlerën e numruesit pra
1. Ndryshorja e kontrollit numruesi pastaj inkrementohet në shprehjen numruesi++ dhe cikli fillon
prap me kushtin për vazhdimin e ciklit. Pasi ndryshorja kontrolluese tani është e barabartë me 2
vlera e fundit nuk është arritur kështu që programi e ekzekuton trupin e urdhëresës prap. Ky proces
vazhdon përderisa ndryshorja e kontrollit numruesi të inkrementohet deri në 11. kur të arrihet kjo
vlerë kushti i vazhdimit të ciklit nuk vlenë dhe përsëritja ndërpritet. Programi vazhdon me
ekzekutimin e urdhëresës së parë pas strukturës for (në këtë rast urdhëresës return në fund të
programit).
Struktura përsëritëse for i shfrytëzon të gjitha detalet e numruesit kontrollues të përsëritjeve.
Prandaj struktura përsëritëse for mund të shprehet edhe nëpërmes strukturës while (figurën.12)
(shembulli 6).
Bazat e gjuhës programuese C++ S. Bekteshi 53

Llogaritja e vlerës numerike të faktorielit: F=n! nëse është dhënë vlera e variablës n.

Fillimi

// Programi Prg5_1
#include <iostream> n
int main()
{ F=1
int n,i;
double F;
cout << "Vlera hyrëse n: "; i=1
cin >> n;
F=1;
F=Fi
for (i=1;i<=n;i++)
F=F*i;
cout << "Faktorieli F="<< F<< "\n"; i=i+1
return 0;
Po
} i≤n
Jo
Dalja:
Vlerat hyrëse n: 3 F
Faktorieli F=6
Fundi

Llogaritja e vlerës numerike të funksionit: Fillimi


y=x2+3x-(3n-2)!
nëse janë dhënë vlerat e variablave m, n dhe x.
n
#include <iostream>
int main() F=1
{
int n,i;
double F; i=1
cout << "Vlera hyrëse n dhe x: ";
cin >> n >> x;
F=1; F=Fi

for (i=1;i<=3*n+2;i++) i=i+1


F=F*i;
y=x*x+3*x-F; Po
cout << "Vlera e funksionit y=" << y<< "\n"; i≤n
return 0; Jo
} 2
y=x +3x-F
Dalja:
Vlerat hyrëse n dhe x: 3 y
Vlera e funksionit y=
Fundi
Bazat e gjuhës programuese C++ S. Bekteshi 54

n
 i
Të llogaritet vlera e funksionit: y  3 x  2 n  2 !  nëse janë dhënë vlerat e variablave x dhe
i 1  3
n. Fillimi

x,n

 1  2  n 
y  3x  2n  2 !   n  2 !   ...n  2 !   F=1
 3  3  3 

i=1
// Programi Prg5_11

#include <iostream> F=Fi


int main()
{ i=i+1
int n,i;
double x,y,F,s; Po
i≤(n+2)
cout << "Vlerat hyrëse n dhe x: ";
cin >> n >> x; Jo
F=1;
s=0
for (i=1;i<=n+2;i++)
F=F*i; i=1
s=0;
s=s+(F+i/3)
for (i=1;i<=n;i++)
s=s+(F+i/3.);
y=3*x-2*s; i=i+1

cout << "Vlera e funksionit y="<< y<< "\n"; Po i≤n


return 0; Jo
}
y=3x-2s
Dalja:
Vlerat hyrëse n dhe x: 2 3
Vlera e funksionit y=-89 y

Fundi
Bazat e gjuhës programuese C++ S. Bekteshi 55

Struktura e zgjedhjes së shumëfishtë switch

Deri më tash kemi diskutuar strukturën e zgjedhjes së njëfishtë if dhe strukturën e zgjedhjes
së dyfishtë if-else. Nganjëherë algoritmet mund të përmbajnë vargun e vendimeve në të cilat
testohen ndaras ndryshorja ose shprehja për çdo vlerë konstante që mund të supozohet dhe aksione
të ndryshme që mund të mirren.
Struktura switch përbëhet nga vargu i rasteve case dhe case-it opcional default.
Shembulli.8

Diagrami i rrjedhjes së strukturës së zgjedhjes së shumëfishtë switch është dhënë në fig. 11.

Fillimi

Saktë case a
case a break
aksioni(et)

Pasaktë

Saktë case a
case b break
aksioni(et)

Pasaktë

Saktë case a
case c break
aksioni(et)

Pasaktë

aksioni
default

Fundi

Fig.11 Diagrami i rrjedhjes së strukturës switch

Urdhëresat break dhe continue

Urdhëresa break kur ekzekutohet në strukturat while, do-while, for dhe switch shkakton
daljen e menjëhershme nga struktura në të cilën gjendet. Ekzekutimi vazhdon në deklaratën e parë
pas strukturës. Urdhëresa break përdoret për kërcimi të parakohshëm nga struktura ose ti shmanget
mbetjes së strukturës switch.

1. // prg8. Përdorimi i urdhëresës break në strukturën for


2. #include <iostream.h>
3.
4. int main()
5. {
6.
Bazat e gjuhës programuese C++ S. Bekteshi 56

7. int x; // x deklarohet këtu që të mund të përdoret pastaj në cikël


8.
9. for ( x = -1; x <= 10; x++ )
10. {
11. if ( x == 0 )
12. break; // E ndërpren ciklin vetëm nëse x është 0
13. cout << x << " ";
14. }
15. cout << "\nCikli i ndërpritur pasi x është " << x << endl;
16. return 0;
17. }

Analizë: Në programin e mësipërmë kur struktura if heton se vlera e x është 0 (rreshti 11), break
ekzekutohet dhe cikli for ndërpritet. Programi vazhdon me cout pas strukturës for në rreshti 15.
Cikli ekzekutohet vetëm një herë. Të theksojmë se në rreshtin 7, ndryshorja x është definuar jashtë
strukturës for pasi qëllimi i jonë ishte përdorimi i ndryshores x brenda dhe jashtë strukturës for
(shiko ndryshoret lokale dhe globale).

Urdhëresa continue kur ekzekutohet në ciklin while, do-while, for i kalon urdhëresat e
mbetura në trupin e strukturës në të cilën gjendet dhe vazhdon me iteracionin tjetër të ciklit. Në
strukturat while dhe do-while, testi për vazhdimin e ciklit zhvillohet menjëherë pasi të ekzekutohet
urdhëresa continue. Në strukturën for pasi të ekzekutohet shprehja për inkrementim pastaj
zhvillohet testi për vazhdimin e ciklit. Më parë kemi theksuar se struktura while mund të përdoret
për paraqitjen e strukturës for. Kjo nuk vlenë vetëm në astin kur shprehja për inkrementim në
strukturën while pasohet me urdhëresën continue. Në këtë rast inkrementimi nuk ekzekutohet para
se të testohet kushti për vazhdimin e përsëritjes she while nuk e ekzekuton në mënyrë të njejtë si
edhe for.
Prg9 e përdor urdhëresën continue në strukturën for që ta kalon urdhëresën dalëse në
strukturë dhe fillon iteracionin tjetër të ciklit.

1. // Prg9. Përdorimi i urdhëresës continue në strukturën for


2. #include <iostream.h>
3.
4. int main()
5. {
6. for ( int x = -1; x <= 10; x++ ) {
7. if ( x == 0 )
8. continue; //e kalon kodin e mbetur të ciklit vetëm nëse x është 0
9.
10. cout << x << " ";
11. }
12. cout << "\n continue është përdorë për ta kalue shtypen e vlerës 0" << endl;
13. return 0;
14. }
Bazat e gjuhës programuese C++ S. Bekteshi 57

6. Funksionet, ndryshoret dhe fushëveprimi i tyre

Në këtë kapitull do të sqarojmë se për çka na nevojiten funksonet, si deklarohen ato dhe si i
thrrasim dhe kthehemi nga ato. Shumica e programeve që shërbejnë për zgjidhjen e problemeve të
caktuara janë më të mëdha se programet e paraqitura deri më tash. Problemet e ndërlikuara zgjidhen
me ndarjen e tyre në një numër më të madh të problemeve të vogla (module) të cilat mund të
menagjohen më lehtë. Në këtë mënyrë arrijmë tek kuptimi programimit modular. Modulet në C++
quhen funksione dhe klasa.
Programet e C++ zakonisht shkruhet me kombinimin e funksioneve dhe klasave të shkruara
mga vet programuesi dhe funksioneve dhe klasave që janë në dispozicion në bibliotekën standarde
të C++. Biblioteka standarde e C++ ka një koleksion të pasur të funksioneve që kryejnë tllogaritje ë
zakonshme matematike, manipulimin me stringje, manipulimin me karaktere, kërkimin e gabimeve
hyrëse/dalëse dhe shumë operacione tjera.
Programuesi mund të shkruaj funksione që të definoj detyra specifike që mund të përdoret
në shumë pika në program. Këto quhen funksione të definura nga programuesi. Urdhëresat që e
definojnë funksionin shkruhen vetëm njëherë dhe këto urdhëresa janë të fshehura për funksionet
tjera.

Funksionet dhe ekzekutimi i tyre

Funksioni është tërësi e deklarimeve të organizuara në mënyrë të caktuar. Një funksion është
pjesë pavarur e kodit të C++ i cili e ka emrin dhe kryen një detyrë të caktuar që mund të kthej një
vlerë në programin thirrës. Ti sqarojmë këto që thamë më lartë:
o Funksioni është pjesë pavarur e kodit të C++ Përkthyesi i C++ funksonin e trajton si një
tërësi të veçant programore
o Funksioni e ka emrin e vet. Çdo funksion e ka emrin e vet unikat të njejtin emër nuk guxon
ta ketë asnë funksion ose ndryshore tjetër). Me përdorimin e emrit në pjesë tjetër të
programit ekzekutohen urdhëresat të cilat i përmban funksioni. Kjo njihet si thirrrje e
funksionit. Një funksion mund të thirret nga funksioni tjetër. Për ngjitjen e emrave të
funksioneve vlejnë të njejta rregulla si emërtimet e ndryshoreve.
o Një funksion kryen një detyrë të caktuar. Detyra është një punë diskrete që duhet ta kryej
funksioni si pjesë e programit siç është psh llogaritje të ndryshme, dërgimi i një rreshti të
tekstit në shtypës, klasifikime të ndryshme etj.
o Një funksion mund të kthej një vlerë në programin thirrës. Kur programi e thirr një
funksion, urdhëresat që i përmban ai ekzekutohen. Këto urdhëresa mund ti dërgojnë
informatat prapa në programin thirrës nëse ato na nevoiten.
Një program i C++ nuk i ekzekuton urdhëresat në funksion përderisa funksioni nuk thirret
nga ndonjë pjesë tjetër e programit. Kur të thirret funksioni, programi mund ti dërgoj informata
funksionit në formë të një ose më shumë argumenteve. Një argument është një e dhënë e programit
që i duhet funksionit për të kryer një detyrë të caktuar. Urdhëresat në funksion ekzekutohen pastaj
duke e kryer qëllimin për të cilat janë shkruar. Kur kryhen urdhëresat e funksionit, ekzekutimi
kthehet prapa në të njejtin vend në program që e ka thirrë funksionin. Funksionet mund ti dërgojnë
prapa informacionet në program në formë të një vlere kthyese.
Çdo herë kur të thirret funksioni, ekzekutimi dërgohet (kalon) në atë funksion. Kur të
përfundon funksioni, ekzekutimi dërgohet prapa në vendin prej të cilot funksioni ishte thirr. Një
funksion mund të thirret aq herë sa të nevoitet.
Bazat e gjuhës programuese C++ S. Bekteshi 58

Deklarimi (prototipi) dhe definimi i funksioneve

Më parë kemi theksuar se para se të përdoret ndryshorja duhet të deklarohet ose të definohet.
Edhe për funksionet vlen e njejta gjë. Funksionet duhet të deklarohen ose të definohen para se të
thirren.
Përdorimi i funksioneve në program kërkon që së pari të deklarohet e pastaj të definohet
funksioni. Deklarimi i tregon kompajllerit emrin, tipin kthyes dhe parametrat e funksionit.
Definicioni i tregon kompajllerit se si punon funksioni. Asnjë funksion nuk mund të thirret prej
funksionit tjetër nëse më parë nuk është i deklaruar. Deklarimi i funksionit quhet prototipi i tij.

Definimi i funksionit

Definimi i funksionit kërkon nga kompajlleri i C++ të rezervoj memorje për ndryshoren ose
funksionin e emruar me një identifikator. Forma e përgjithshme e definimit të funksionit është :
tipi_kthyes emri_funksion( lista e parametrave);
{
deklarata(t)
urdhëresa(i)
....................
urdhëresa_kthyese
}
Definimi i funksonit përbëhet nga :
- tipin e vlerës kthyese,
- emri i funksonit, Kreu i funksionit
- lista e parametrave dhe
- trupi i funksonit
Tri elemetet e para e formojnë kreun e funksonit. Këto elemente e përbëjnë të gjitha
informatat e nevojshme që funksioni të thirret dhe të shfrytëzohet në mënyrë të drejtë, por nuk n’a
tregojnë asgjë se si e kryen funksioni punën e vet. Kjo është detyrë e trupit të funksonit.
Funksoni nuk definohet asnjëherë brenda funksonit tjetër. Të gjitha kodet e funksoneve në
programe duhet të jenë sekuenciale, dmth njëra pas tjetrës. Kllapa që e mbyll funksonin duhet të
jetë para kodit të funksionit të ardhshëm .

Kreu i funksionit

Kreu i funksonit e përmban identifikatorin (emrin e funksionit ) çiftin e kllapave (dhe) me


listën opcionale të parametrave të funksionit dhe definicionit të parametrave të funksionit. Ai n’a
rregon në tipin e të dhënave të cilën e kthen funksioni nëse eventualisht e kthen vlerën.

tipi_kthyes emri_funksion( lista e parametrave);

Tipi i vlerës se kthyer mund të jetë çfardo tipi i të dhënave ose tipi i nxjerrur. Është e qartë
se tipit int, float, char e kështu me radhë, janë tipe të përshtatshme për vlerën e kthyer. E njëjta gjë
vlen edhe për void që dmth se funksioni nuk kthen kurrfarë vlere.
Bazat e gjuhës programuese C++ S. Bekteshi 59

Shembull: Nëse funksioni e llogaritë vlerën reale me precizitet të zakonshëm atëhere tipi i vlerës
kthyese është float ose nëse kemi:
int funksioni1(...) // kthen një tip int.
souble funksioni2(...) // kthen një tip double.
void funksioni3(...) // nuk krhen asgjë.

Me rëndësi është gjithashtu edhe identifikatori i funksionit. Për emërtimin e funksioneve


vlejnë të njejtat rregulla si edhe emërtimi (identifikatorin) i ndryshoreve.
Elementi i fundit i kreut të funksionit është lista e parametrave për të cilën do të sqarojmë
më detalisht në vazhdim.

Lista e parametrave

Shumë funksione i përdorin argumentet të cilat janë vlera të dërguara në funksion kur ai
thirret. Funksioni duhet ta dij se çfarë llojit të argumenteve të pres – tipin e të dhënave për çdo
argument. Funksionit mund ti dërgohet çdo tip i të dhënave të C++. Informatat e tipit të argumentit
jipet në kreun e funksionit me listën e parametrave.
Lista e parametrave është lista e ndarë me presje që përmban deklaratat e parametrave që
pranohen nga funksioni kur ai të thirret. Për çdo argument që i dërgohet funksionit, lista e
parametrave duhet të ketë nga një vend. Ky vend përcakton tipin e të dhënave dhe emrin e
parametrit. Nëse funksioni nuk pranon asnjë vlerë, lista e parametrave është void ose rhjesht është e
zbrazët. Në listën e parametrave të funksionit duhet të shkruhet gjithsesi mënyrë eksplicite tipi për
çdo parametër.

Shembull: Për kreun e funksionit:


long funksioni1(long x)
lista e parametrave përbëhet nga long x, që përcakton se ky funksion ka një argument të tipit long
që paraqitet me parametrin x. nëse kemi më shumë se një parametër ata duhet të ndahen me presje:
long funksioni1(int x, float y, char z)
që tregon se funksioni ka tri argumente: një të tipit int me emër x, një të tipit float me emër y, dhe
një të tipit char me emër z. Disa funksione nuk kanë argumente, në këtë rast lista e paramatrave
është e zbrazët ose duhet të përmbaj void si në vijim:
void funksioni1()
void funksioni1(void)

Trupi i funksionit

Trupi i funksionit shpesh quhet bllok dhe është vendi ku kryhet puna. Ai paraqet tërësinë e
deklaratave ekzekutuese, deklaratave të zakonshme dhe të ndryshoreve që përdoren në funksion.
Deklaratat e ndryshoreve duhet të shkruhen para deklaratave ekzekutuese prg,28.
Kllapat e mëdha shënojnë fillimin dhe fundin e trupit të funksionit. Rrjedhja e ekzekutimit
kur kalon në funksionin e thirrur po kalon në urdhëresën e parë ekzekutuese në trupin e funksionit.
Ekzekutimi del nga funksioni përmes urdhërave drejtuese siç janë: return, abort dhe exit ose thjesht
duke kaluar fundin e trupit të funksionit (kllapa e madhe e djathtë). Kllapat e formojnë bllokun nga
urdhëresat të cilat i rrethojnë. Brenda bllokut funksional mund të keni blloqet e brendshme.

Shembull:
Bazat e gjuhës programuese C++ S. Bekteshi 60

double katrori( double numri ) // Kreu i funksionit


{ // hapja e kllapës
return( numri * numri ); // Trupi i funksionit
} // Mbyllja e kllapës
void Shtypja( int pyetja )
{
if(pyetja == 1 )
puts( "Shtypet rezultati" );
else
puts( "Nuk shtypet rezultati" );
}

1. //prg.28 Llogaritë shumën e katrorëve


2. #include <iostream.h>
3. #include <conio.h>
4. shuma_katror(n) //Kreu i funksionit
5. int n;
6. {
7. int i; //Trupi i funksionit janë të gjitha urdhëresat në mes të kllapave
8.
9. long shuma=0;
10. for (i=1;i<=n;shuma+=(long)i*i,++i);
11. cout<<"Shuma e katroreve prej 1deri "<<n<<" është \n"<<shuma;
12. }
13.
14. main ()
15. {
16. shuma_katror(40);
17. getch();
18. return 0l
19. }
Dalja: Shuma e katroreve prej 1deri 40 ështe
22140

Anakizë: Identifikatori shuma_katror në kreun e funksionit është emri i funksonit me të cilin


identifikohet funksioni dhe thirret nga funksioni main() ose nga funksionet tjera. Në mes të kllapave
paraqitet parametri i këtij funksioni kurse të gjitha urdhëresat tjera në mes kllapave të mëdha
paraqesin trupin e funksionit. Pra, për definimin e funksionit janë të domosdoshme identifikatorët
(emri i funksionit), kllapat e vogla dhe kllapat e mëdha, Urdhëresa që gjendet në main():
shuma _katrore (40);
tregon se në atë vend duhet të ekzekutohet llogaritje e shumës së katrorëve. Në atë vend kontrolla e
programit drejtëpërsëdrejti bartet në funksionin shuma _katrore dhe ekzekutohet trupi i funksionit
me ç’rast llogaritet shuma e katrorëve dhe shtypet lajmërimi :
Shuma e katrorëve prej 1 deri në 10 është 22140
Funksioni shuma_katror përbëhej vetëm prej një parametri n. Parametrat formalë duhet të
definohen në fillimin e funksionit, pas deklarimit të tij dhe para kllapës së parë të madhe. Në
funksionin shuma_katror është urdhëresa:
int n;
me të cilën parametri formal n definohet i tipit int.
Bazat e gjuhës programuese C++ S. Bekteshi 61

Pas kreut të funksionit është definuar trupi i tij. Pasi dëshirohet të llogaritet shuma e
katrorëve prej 1 deri në n nevoiten dy ndryshore, ndryshorja i për kontrollimin e ciklit for dhe
ndryshorja shuma për agregimin e shumës së katrorëve gjatë llogaritjes. Ndryshorja i është
deklaruar e tipit int, ndërsa shuma si long int. Deklarimi dhe inicializimi i ndryshoreve është i njëjtë
si tek funksioni main.
Në këtë program funksioni main() e thirrë funksionin shuma_katror dhe si vlerë të
parametrit formal e specifikon 40. Parametri 40 është parametri i vërtetë i funksionit sepse me atë
vlerë të parametrit ekzekutohet me të vërtetë funksioni. Parametri i vërtetë duhet të jetë i tipit të
njëjtë si edhe parametri formal. Funksioni main mund ta thirrë funksionin shuma _katror edhe më
shumë herë me vlera të tjera të parametrit të vërtetë.

Deklarimi i funksionit

Ekzistojnë tri mënyra për deklarimin e funksionit:


 Prototipi i funksionit shkruhet në një fajll e pastaj duke e përdor direktivën #include
përfshihet në program.
 Prototipi i funksionit shkruhet në fajllin në të cilin përdoret funksioni.
 Definohet funksioni para se të thirret nga një funksion tjetër. Në këtë rast, definicioni vepron
sikurse edhe vet deklarimi i tij.
Praktikë e mirë programore është që gjithëmonë të shkruhet prototipi i funksionit edhe pse
mund ti shmangemi domosdoshmërisë së shkruarjes së tij.

Prototipi i funksionit

Tek ndryshoret deklarimi i saj është i njejtë me definimin e saj, por kjo nuk vlen edhe për
funksionin. Deklarimi i funksionit është paralajmrim për një funksion i cili është definuar diku
tjetër dhe përcakton se çfarë vlere kthehet nga funksioni. Definimi i funksionit e definon se çka bën
funksioni si dhe jep numrin dhe tipin e argumenteve që barten në funksion.
Forma e përgjithshme e deklarimit (prototipit) të funksionit është:
tipi_kthyes emri_funksion(lista e parametrave);
Prototipi i funksionit ndërtohet ashtu që kreut të funksionit i shtohet një pikë-presje.
Prototipi i funksionit i tregon përkthyesit se çka të pret kur më vonë, në program, të thirret
funksioni. Prototipi e përcakton tipin e vlerës së kthyer, emrin e funksionit dhe tipet e të gjithë
argumenteve që priten. Përveç rasteve kur funksioni të cilat marrin numër të ndryshëm të
argumenteve, prototipi e përcakton gjithashtu edhe numrin e argumenteve. Të gjitha këto informata
i ndihmojnë përkthyesit që të shqyrtoj se kodi burimor i juaj a i shfrytëzon saktë dhe në mënyrë
konsistente funksionet. Në këtë mënyrë i largohemi gabimeve të mundshme.

Shembull: Prototipi i funksionit shuma duket kështu:


void shuma (int,char);
Nëse i vendosni emrat e parametrave, atëherë duket kështu:
void shuma (int n, char c);
ose prototipi i funksionit Katrori:
double Katrori( double numri);
Bazat e gjuhës programuese C++ S. Bekteshi 62

Prototipi i funksionit dhe definicioni i funksionit duhet të pajtohen plotësisht sipas tipit
kthyes emrit dhe listës së parametrave. Në të kundërtën kompajlleri do të lajmëroj për gabim. Të
theksojmë se në listën e parametrave duhet të shënohen vetëm tipet e të dhënave të parametrave.
Për dokumentim më të mirë, në atë listë mund të vendosen edhe emrat e parametrave. Përkthyesi
ata emra nuk i merr në shqyrtim.. Yë gjitha këto që u thanë më lartë janë sqaruar në prg7

1 // Prg7 : Krijimi dhe përdorimi i funksioneve të definuara nga programuesi


2
3 #include <iostream.h>
4
5 int katrori( int ); // Prototipi i funksionit
6
7 int main()
8 {
9 for ( int x = 1; x <= 10; x++ )
10 cout << katrori( x ) << " ";
11
12 cout << endl;
13 return 0;
14 }
15
16 // Definitmi i funksionit
17 int katrori( int y )
18 {
19 return y * y;
20 }

Analizë: Çdo program që e kemi paraqitë deri tash e ka pasë fuksionin thirrës main() që i ka thirrë
funksionet e bibliotekës standarde të kryejnë detyra të caktuara. Funksioni katrori është thirrë në
main() me:
katrori (x)
funksioni katrori pranon një kopje të vlerës x në parametrin y. Pastaj katrori e llogaritë y*y rezultati
kthehet prapa në pikën në main ku katroti është thirrë dhe rezultati paraqitet. Të theksojmë se vlera
e x nuk ndryshon me thirrjen e funksionit. Ky proces përsëritet dhjetë herë duke e përdore
strukturën përsëritëse for. Definicioni i katrorit tregon se katrori e pret një parameter të tipit int.
Fjala e rezervuar int para katrori tregon se katrori e kthen rezultatin e tipit int. Urdhëresa return në
funksonin katrori e dërgon rezultatin e llogaritur prapa në funksionin thirrës.
Në rreshtin 5, int katrori (int); është prototip i funksonit. Tipi i të dhënave int brenda
kllapave e informon kompajllerin se funksioni katrori pret një vlerë integer nga funksioni thirrës. int
para emrit katrori e informon kompajllerin se katrori e kthen rezultatin të tipit int në funksionin në
funksionin thirrës. Kompajlleri i referohet prototipit të funksionit të hulumtoj se thirrja e katrori
përmban tip korrekt kthyes, numër korrekt i argumenteve, tipe korrekte të argumenteve dhe se
argumentet janë në radhë korrekte.

Fajllat header

Shumë funksione të gatshme i kanë prototipet e funksioneve janë të shkruara në fajllat të


cilat përfshihen në protjram me ndihmën e #include. Çdo bibliotekë standarde i ka fajllat
përkatëse header që përmbajnë prototipet e funksioneve për të gjitha funksionet në atë bibliotekë
Bazat e gjuhës programuese C++ S. Bekteshi 63

dhe definicionet e tipeve të ndryshme të të dhënave dhe konstanteve që iu nevoiten këtyre


funksioneve. Në tabelën janë dhënë disa fajlla të zakonshme header të bibliotekës standarde të C++.
Duhet të themi se fajllat header që mbarojnë me h janë të „tipit të vjetër“. Ekziston biblioteka e re
standarde e C++. Programuesi mund të krijoj fajlla të zakonshëm header. Fajllat header të definuara
nga programuesi duhet të mbarojnë me .h. Fajllat header të definuara nga programuesi mund të
përfshihen në program me urdhëresën preprocesorike #include. .

Shembull: a) Fajlli header katrori.h mund të përfshihet nëse në krye të programit shkruajmë:
#include<katrori.h>

Nëse ndërtoni biblioteka të funksioneve me të vërtetë kursehet koha. Përndryshe në çdo


program janë shfrytëzuar funksoniet e bibliotekës standarde të gjuhës C++. Kur e shkruani kreun
iostream.h ju në të vërtetë keni futur një grup të prototipeve të funksioneve për funksionet standarde
hyrëse dhe dalëse.

Shembull: b) Unë e kam përdor funksionin cout pothuajse në çdo program. Çdo herë më është
dashtë ta përfshij fajllin header iostream.h. sepse fajlli header përmban deklaratën e cout e cila e
sinjalizon kompajllerin për tipin kthyes dhe prototipin e funksionit. Definicioni i cout gjendet në një
vend tjetër.

Funksionet e bibliotekës math. e lejojnë programuesin të kryej llogaritjet e zakonshme


matematike. Funksionet thirren me deklarimin (definimin) e tij

Shembull: c) Nëse dëshirojmë të llogarisim rrënjën katrore të 900, atëhere shkruajmë:


cout <<sqrt(900.0);
kur urdhëresa ekzekutohet, funksioni sqrt i biliotekës math thirret për të llogaritur rrënjën katrore të
numrit i cili gjendet brenda kllapave (numri 900.0 në rastin tonë) Numri 900 është argument i
funksionit sqrt. Urdhëresa e mësipërme do të shtyp numrin 30. Funksioni aqrt ka një argument të
tipit double dhe e kthen rezultatin të tipit double.

Argumentet e funksionit mund të jenë konstante, ndryshore dhe shprehje.

Shembull: Rasti kur si argument i funksionit është shprehja.


Nëse a1=13.0, a2=3, a3=4 atëhere:
cout <<sqrt(a1 + a2*a3);
e llogaritë dhe e shtyp rrënjën katrore të shprehjes 13.0 + 3.0*4.0=35.0 pra 5.

Të gjitha funksionet në bibliotekën math i kthejnë të dhënat të tipit double. Nëse dëshirojmë
ti përdorim funksionet e bibliotekës math duhet të përfshihet (duhet të shkruhet) fajlli header
math,h. (ky fajll header në bibliotekën e re standarde të C++ quhet cmath.h). Disa funksione
matematike janë paraqitur në tabelën.8

Parametrat dhe argumentet e funksionit

Parametrat dhe argumentet janë dy emra të ndryshëm për të njëjtën gjë, të shiquar nga
aspekte të ndryshme. Nga aspekti i definimit të funksionit vlerat në listë nën kllapa pas funksionit
quhen parametra formal kurse nga aspekti i funksionit i cili i thirrë vlerat e dhëna funksionit të
thirrur quhen argumente të vërtetë. Të dhënat që dërgohen quhen parametra ndërsa të dhënat që
pranohen quhen argumente të funksionit.
Bazat e gjuhës programuese C++ S. Bekteshi 64

Një argument është vlera që i dërgohet funksionit nga programi thirrës. Çdo herë kur të
thirret funksioni atij mund ti dërgohen argumente të ndryshme. Në C++, një funksioni duhet ti
dërgohen numri dhe tipi i njejtë i argumenteve për çdo herë që thirret, por vlerat e argumentiti mund
të jenë të ndryshme. Në funksion, argumentit i çasemi duke e përdorë emrin përkatës të parametrit.
Parametri është ndryshorja e cila krijohet në stekun e programit në momentin e thirrjes së
funksionit. Kjo ndryshore përdoret që t’i ruhet vendi dhe nëpërmjet emrit të tij merren të dhënat që i
jipen.

Thirrja dhe kthimi i funksioneve

Deri më tani shpesh jemi takuar me shprehjet „thirrja e funksionit“ dhe „kontrolla kthyese“.
T’i sqarojmë këto shprehje më detalisht.
Thënë në përgjithësi, funksioni që kontrollon thirrjet e funksionit dhe shkallën e tyre quhet
funksion thirrës. Funksioni që kontrollohet prej funksionit thirrës quhet funksion i thirrur. Që të
thirret një funksion, thjesht shkruhet emri i funksionit (duke përfshirë kllapat dhe në fund
pikëpresje).

Shembull: a) Një funksion thirret A function is invoked (dmth është ndërtuar që të kryej detyrën e
destinuar) nga funksioni thirrës. Funksioni thirrës specifikohet me emrin e funksionit dhe jep
informata (si argumente) që funksioni i thirrur duhet të kryej punën e tij. Një analogji me këtë është
hierarkia e menagjimit. Shefi (në rastin tonë funksioni thirrës) kërkon nga punëtori1 (funksioni i
thirrur) të kryej detyrën dhe të kthej (return) (të jap përsëri raport) për rezultatet e punës së kryer.
Shefi (funksioni thirrës) nuk e din se si punëtori1 (funksioni i thirrur) e kryen punën e destinuar.
Punëtori1 mund të thirrë punëtorë tjerë (punëtori2, punëtori3 etj) dhe shefi të mos jetë i njohtuar për
këtë. Në këtë rast punëtori1 (funksioni i thirrur) është shef (funksion thirrës) për punëtori2,
punëtori3 etj. Kjo procedurë mund të vazhdoj edhe mëtutje sipas nevojës.

Që dy funksione ti përdorin të njejtat ndryshore duhet që ndryshoret të iu dërgohen


funksioneve – ngjashëm kur qendërmbrojtësi (funksioni thirrës) ia dërgon futbollin ndonjë
futbollisti tjetër (funksioni pranues). Në vazhdim do të sqarohet se si bëhet dërgimi i të dhënave nga
një funksion në funksionin tjetër, ndërsa më vonë do të shohim se si kthehet vlera nga një funksion
në funksionin tjetër ( prg.25 ).
Bazat e gjuhës programuese C++ S. Bekteshi 65

//Prg.25
#include <iostream.h>
#include <conio.h>
int Funks1(),Funks2();
main() /*Funksioni main ekzekutohet i pari*/
{
cout<<"\n Funksioni i parë quhet main \n";
Funks1();
Funks2();

cout<<"Funksioni main është kompletuar\n";


getch ();
return 0;
}
Funks1()
{
cout<<"(Brenda Funks1\n";
return 0;
}

Funks2()
{
cout<<"Brenda Funks2\n";
return 0;
}
Dalja:
Funksioni i parë quhet main
Brenda Funks1
Brenda Funks2
Funksioni main është kompletuar

Analizë: Shembulli i mësipërm paraqet mënyrën e ekzekutimit të programit. Funksioni main e


kontrollon se cili nga funksionet thirret në radhën e tyre. Kontrolla gjithmonë kthehet të funksioni
thirrës pasi të mbaron funksioni i thirrur.
Funksioni shuma_katror i kryen llogaritjet e caktuara dhe shtypet rezultati i llogaritjes.

Kur funksioni duhet të punoj me vlera, funksionin thirrës i dërgon vlerat brenda kllapave.
Kodi i funksionit pranues ka grupin e ngjashëm të kllapave me ndryshore brenda tyre që ti pranoj të
dhënat. Të dhënat që dërgohen quhen parametra ndërsa të dhënat që pranohen quhen argumente të
funksionit. Zakonisht një funksion nuk ka qasje në të dhënat lokale të tjetrit. Megjithate nëse
funksioni i dërgon një ose më shumë vlerat e të dhënave të veta si argumente, funksioni tjetër mund
ti pranoj ato të dhëna dhe të punoj si të kishte qasje gjithëmonë.

Shembull: b) main() i dërgon dy vlera integer, v1 dhe v2, funksionit Merrvlera(), main() mund ti
dërgon vlerat si vijon:
Merrvlera(v1, v2); // E thirr funksionin Merrvlera() dhe i jep dy vlera
Dy rreshtat e parë të Merrvlera(v1, v2) mund të duken si vijon:
void Merrvlera(int v1, int v2);
{
Bazat e gjuhës programuese C++ S. Bekteshi 66

void main() Merrvlera(int v1, int v2)


{ {
// vazhdon pjesa e parë e main() // vazhdon trupi i Merrvlera ()
// Merrvlera () mund të punoj me v1
// dhe v2 sikur këto ndryshore të
Merrvlera (v1, n2); //dërgon dy vlera
// ishin lokale në këtë funksion

// Pjesa tjetër e main() return;


return; }
}

Ekzistojnë tri mënyra për dërgimin e të dhënave nga njëri funksion në funksionin tjetër.
 Përmes vlerës
 Përmes adresës
 Përmes referencës
Se cilën metodë do të përdoret varet nga ajo se funksioni pranues a duhet me qenë në gjendje
me i ndërrue ndryshoret e funksionit thirrës. Tash do të sqarohet dërgimi përmes vlerës ndërsa më
vonë përmes adresës dhe references.

Dërgimi përmes vlerës

Dërgimi përmes vlerës nganjëherë quhet edhe dërgim përmes kopijimit. Kur të dërgohet një
argument nga një funksion në funksionin tjetër, vlera e argumentit i dërgohet funksionit pranues,
ndërkaq vet ndryshorja nuk i dërgohet. Dërgimi sipas vlerës dmth se se funksioni pranues nuk mund
ta ndryshoj ndryshoren e funksionit dërgues në asnjë mënyrë. Pra dërgohet - vetëm vlera e
ndryshores së funksionit dërgues – por jo edhe vet vlera. Kur vlera arrin në funksionin pranues,
funksioni pranues e pranon atë vlerë në parametrin e vet të ndryshores lokale dhe punon me
ndryshoren e vet që përmban vlerën e dërguar. Megjithate, funksioni pranues asgjë nuk do të
ndryshoj në funksionin dërgues prg.26.
Kur funksioni pranon më shumë se një parametër, tipit e të dhënave të pranuara poashtu
ndahen me presje.

Shembull: Nëse main() e dërgon një integer të emruar me i, një karakter të emruar me c, dhe një
vlerë me presje dhjetore të emruar me x në funksionin Merr_vlera (), rreshti në main() mund të
duket si vijon:
Merr_vlera (i, c, x); // Dërgon tri vlera
Definicioni i Merr_vlera () mund të duket si vijon:
void Merr_vlera (int i, char c, float x) // rreshti i definimit
Siç theksuam edhe më parë, Merr_vlera () mund ti riemroj vlerat e argumenteve dhe ti
përdor emrat e rij si parametra të tij por Merr_vlera () kurrë nuk mund ti ndryshoj kopjet e main()
për asnjë ndryshore.

1.: // Prg.26 Dërgon një argument prej main() në funksionin tjetër përmes vlerës
2.:
3.:
Bazat e gjuhës programuese C++ S. Bekteshi 67

4.: #include <iostream.h>


5.:
6.: void Merrvlera (int i); // Prototipi i funksionit
7.:
8.: void main()
9.: {
10.: int i;
11.:
12.: cout << "Tash jam në main()... " << endl;
13.: cout << "Shtype një vlerë për i: ";
14.: cin >> i;
15.: 3
16.: Merrvlera (i); // ska tip të të dhënave, vetëm ndryshorja
17.:
3 18.: cout << endl << endl;
19.: cout << "Prapa në main(), vlera është akoma "
20.: << i << endl;
21.: return;
22.: } 3 3
23.: //---------------------------------------------------------------------------
24.: void Merrvlera (int i)
25.: {
26.: // Merrvlera () tash ka ndryshoren lokale të emërtuar gjithashtu i
27.: cout << endl << endl
28.: <<"Në Merrvlera()i është " << i << endl;
29.:
30.: i *= 5;
31.:
32.: cout << "Pas shumëzimit me 5, i është tash " << i << endl;
33.: return; // kthehet në main()
34.: }
Dalja Tash jam në main()...
Shtype një vlerë për i: 3
Në Merrvlera() i është 3
Pas shumëzimit me 5, i është tash 15
Prapa në main(), vlera është akoma 3

Analizë: Nga dalja shihet se Merrvlera () mund ta ndryshoj i vetëm brenda Merrvlera (). Pas
Merrvlera () e kthen kontrollën në main(), Shihet gjithashtu se i e main() ka mbet e njejtë me vlerën
e tij origjinale. Ndryshorja i e funksionit main() dhe ndryshorja i e funskionit Merrvlera () janë
plotësisht dy ndryshore të ndryshme. Njëra është ndryshore lokale e main() ndërsa tjetra është
ndryshore lokale e Merrvlera ().
main() nuk i ka në list tipin e të dhënave të i në kllapat e rreshtit 16 sepse main() e din tipi e
të dhënave të i. Vetëm funksionit pranues, i cili nuk din asgjë për argumentet para se ti dërgohen
duhet ti tregohet tipi i të dhënave të vlerave që i dërgohen.
Pikëpresja nuk qitet në fund të rreshtit të definicionit të funksionit psh rreshti 24 nuk duhet
kurrë të ketë pikëpresje në fund të tij. Në pikën ku thirret funksioni duhet të qitet pikëpresja si në
rreshtin 16.
Shigjeta tregon se si main() e dërgon vlerën e ndryshores e jo vet ndryshoren në Merrvlera (). Në
këtë rast se shfrytëzuesi ka shtypur 3 siç është tregue edhe në dalje.
Bazat e gjuhës programuese C++ S. Bekteshi 68

Nëse nga main() dërgohet më shumë se një vlerë në Merrvlera (), të gjitha vlerat do të
dërgohen por funksioni pranues nuk mund ti ndryshoj kopjet e main() të ndryshoreve. Kur dërgohen
më shumë se një ndryshore, ndryshoret ndahen me presje

Kthimi i vlerave me return

Më lartë kemi sqaruar se si bëhet dërgimi i të dhënave në funksione. Me ndihmën e


urdhëresës return bëhet kthimi i vlerës në funksionin thirrës. Urdhëresa return i mundëson
funksioneve të kthejnë një vlerë të vetme nga funksioni i thirrur. Pa marrë parasysh se ku është
shkruar urdhëresa return në funksion, ajo e përfundon ekzekutimin e funksionit dhe kontrollën e
kthen në funksionin thirrës.

Shembull: a) Të gjitha urdhëresat e poshtë shënuara janë legale.


1. return 5;
2. return (x > 5);
3. return (Funksioni1());
Kuptohet se Funksioni1())duhet të kthej një vlerë. Vlera në urdhëresën e dytë return (x > 5),
do të jetë zero nëse x nuk ëshët më i madh se 5, ose do të jetë 1. në këtë rast kthehet vlera e
shprehjes , 0 (pasaktë) ose 1 (saktë), e jo vlera e x.

Vlera kthyese e një funksioni mund të përdoret si një argument për funksionin tjetër
Nga një funksion mund të kthehet më së shumti një vlerë. Një funksioni mund ti dërgohen
disa parametra por kthehet vetëm një. Nëse një funksion e kthen një vlerë, funksioni thirrës nuk
është e thënë ta merr atë vlerë. Megjithate, edhepse funksioni thirrës mund të injoroj vlerën e
kthyer, vlera që kthehet duhet gjithëmonë të ekzistoj. Nëse një funksion kthen një vlerë atëhere
duhet të theksohet tipi i vlerës që funksioni e kthen. Në këtë rast duhet që tipi i të dhënave i vlerës
kthyese të shënohet para emrit të funksionit.

Shembull: b) Tipi i të dhënave i vlerës kthyese të shënohet para emrit të funksionit. Prandaj nga
definicioni i funksionit, pa e shiquar urdhëresën return, dihet saktë se çfarë tipi të të dhënave kthen
funksioni.
double Funksion1(int i, float j)
ky funksion kthen një vlerë double. Tipi i të dhënave që kthehet mund të theksohet gjithashtu edhe
në prototipin e funksionit:
double Funksion1 (int i, float j);

Nëse nuk është deklaruar tipi i vlerës kthyese atëhere përkthyesi i C++ sipas definicionit e
kthen vlerën int në programin thirrës. Praktikë e mirë programuese, në mënyrë që ti shmangemi
gabimeve të mundshme, është që gjithmonë në deklarimin e funksionit të shënohet edhe tipi i vlerës
kthyese. .

Shembull: c) Prototipet e funksioneve vijuese janë identike:


int Vlera(int numri, float faktori); //kthehet tipi int
Vlera(int numri, float faktori); //kthehet tipi i nënkuptuar int
Preferohet që gjithëmonë të theksohet tipi i vlerës kthyese edhe nëse ai është int.

Nëse funksioni nuk kthen një vlerë atëhere shënohet void para emrit të funksionit. Void
është një sinjal për kompajllerin se asnjë vlerë nuk do të kthehet.

Shembull: d) Nëse funksioni nuk kthen një vlerë atëhere shënohet void para emrit të funksionit.
Bazat e gjuhës programuese C++ S. Bekteshi 69

void Funksioni(int vlera)

Urdhëresa return mund të përmbaj shprehje e cila duhet të mbyllet në kllapa. Kur urdhëresa
return përmban shprehje atëherë vlera e shprehjes kthehet në funksionin thirrës. prg.27
return (shprehja);
nën supozimin se shprehja jep një vlerë. shembulli a nën 2 dhe 3.
Bazat e gjuhës programuese C++ S. Bekteshi 70

Ndryshoret dhe fushëveprimi i tyre

Tri rregulla vlejnë për mënyrën e përdorimit të ndryshoreve në funksione:


◦ para përdorimit të ndryshores në një funksion ajo duhet të deklarohet në kreun e funksionit
ose në trupin e funksionit (përveç për ndryshoret globale).
◦ Që funksioni të fitoj një vlerë nga programi thirrës, vlera duhet ti dërgohet si një argument.
◦ Që programi thirrës të fitoj një vlerë nga një funksion, vlera duhet në mënyrë eksplicite të
kthehet nja funksioni.
Që të jemi të saktë, këto "rregulla" nuk zbatohen në mënyrë stikte sepse më vonë do të mësojmë
se si ti shmangemi atyre. Megjithate, tash për tash është mire të zbatohen këto rregulla.
Më parë kemi mësuar se ndryshoret mund të definohen:
 pas kllapës së madhe që hap bllokun e kodit (zakonisht në krye të funksionit)
 para emrit të funksionit siç është p.sh. main().
Por kur në program gjenden disa funksione shpesh herë nevojitet që disa ndryshore të kanë
fushëveprim të caktuar. Nga ky aspekt ndryshoret ndahen në ndryshore lokale dhe globale.
Ndryshoret lokale - është nëse dhe vetëm nëse definohet pas kllapës së madhe që e hap
bllokun e kodit (zakonisht në krye të funksionit ).

Shembull: a) Deklarimi i ndryshoreve lokale (pjesa e hijëzuar paraqet fushëveprimin e saj)


main()
{
int i,j; //Ndryshoret lokale i dhe j sepse janë definuar pas kllapës
………………………
}

Ndryshorja globale - është nëse dhe vetëm nëse definohet jashtë funksionit.
Ndryshorja globale vlen prej vendit të definimit r teposhtë kodit burimor,pa marrë parasysh
se sa funksione apo rreshta përmban programi. Deklaratat që janë para ndryshoreve globale nuk
mund t’i përdorin ato ndryshore. Më poshtë po japim shembuj të definimit të ndryshoreve globale
dhe lokale .(pjesa më e errët paraqet fushëveprimin e tyre).

Shembull: b) Deklarimi i ndryshoreve globale (pjesa e hijëzuar paraqet fushëveprimin e saj)


#include<iostream.h>
int i,j; //Ndryshoret globale i dhe j sepse janë definuar para funksionit
main()
{
……………….
}

Përkundrazi ndryshoret lokale vlejnë deri në fund të bllokut të funksionit. Dmth pasi të
kryhet funksioni këto ndryshore shkatrrohen. Dy ndryshore mund të kenë të njejtin emër nëse ato
janë ndryshore lokale në dy funksione të ndryshme. Ato janë ndryshore të ndryshme edhe pse e
kanë të njejtin emër.
Ndryshoret automatike-Sipas definicionit të gjitha ndryshoret lokale janë automatike që dmth se
shkatrrohen kur funksioni i tyre mbaron. Që të definohet një ndryshore si automatike duhet ti
Bazat e gjuhës programuese C++ S. Bekteshi 71

shtohet parashtesa auto e cila është opcionale (nuk është e domosdoshme sepse ato janë edhe ashtu
automatike)

Shembull: c) Deklarimi i ndryshoreve automatike (pjesa e hijëzuar paraqet fushëveprimin e saj)


main()
{
int i; //të theksojmë edhe njëherë se parashtesa auto zakonisht nuk shkruhet
auto float j;
……………………………
}

Ndryshoret statike-Përkundër ndryshoreve automatike kemi ato statike. Sipas definicionit të gjitha
ndryshoret globale janë statike, dmth i ruajnë vlerat e tyre., Nëse një ndryshore lokale është statike
atëherë ajo e ruan vlerën e saj kur përfundon funksioni; në rast se ky funksion thirret për herë të
dytë. që të definohet një ndryshore si statike duhet ti shtohet parashtesa static.

Shembull: d) Deklarimi i ndryshoreve statike (pjesa e hijëzuar paraqet fushëveprimin e saj)


main()
{
int i;
sttatic j=22;
}
Bazat e gjuhës programuese C++ S. Bekteshi 72

Ushtrime: Përdorimi i funksioneve për llogaritjen e integraleve.

 x 
4
Llogaritja e vlerës së integralit:: 2
 1 dx me metodën numerike të Trapezit.
1

// Programi Prg11_1 Fillimi


#include <iostream>

double f(double x); f(x)=x2+1


int main()
{ n,a,b
const int n=10;
const double a=1,b=4;
ba
int i; h
double T,s,h; 2n
h=(b-a)/n;
s=0; s1=0

for (i=1;i<=n-1;i++)
s=s+f(a+i*h); s2=0
T=h*((f(a)+f(b))/2+s);
cout << "Vlera e integralit T="<< T<< "\n";

return 0; s=s+f(a+ih)
}
i=i+1
// Nënprogrami
double f(double x)
Po
{ i≤n-1
return x*x+1; Jo
}
 f (a )  f (b) 
T  h  s
Dalja:  2 

Vlera e integralit T=24.045


T

Fundi
Bazat e gjuhës programuese C++ S. Bekteshi 73

 x 
4
Llogaritja e vlerës së integralit:: 2
 1 dx me metodën numerike të Simpsonit.
1

// Programi Prg11_2
#include <iostream>

double f(double x); Fillimi

int main()
{ f(x)=x2+1
const int n=10;
const double a=1,b=4; n,a,b
int i;
double S,s1,s2,h;
h=(b-a)/(2*n); ba
h
s1=0; 2n
s2=0;
s1=0
for (i=1;i<=n-1;i++)
{
s1=s1+f(a+(2*i-1)*h); s2=0
s2=s2+f(a+2*i*h);
}
s1=s1+f(a+(2*n-1)*h);
S=h/3*(f(a)+f(b)+4*s1+2*s2); s1=s1+f[a+(2i-1)h]
cout << "Vlera e integralit S="<< S<< "\n";
return 0;
} s2=s2+f[a+2ih]

// Nënprogrami
double f(double x) i=i+1
{
return x*x+1; Po
} i≤n-1
Jo
Dalja:
S
h
 f (a)  f (b)  4s1  2s2 
Vlera e integralit S=24 3

s1=s1+f[a+(2n-1)h]

Fundi
Bazat e gjuhës programuese C++ S. Bekteshi 74

24
1
Llogaritja e vlerës së integralit të dyfishtë:   dxdy me metodën numerike të Trapezit.
12 x  y 2
// Programi Prg11_3
#include <iostream>
#include <cmath>

double f(double x,double y);


Fillimi
int main()
{ 1
const int m=6,n=4; f ( x, y ) 
const double a=1,b=2,c=3,d=4; x  y 2
int i,j;
double T,s1,s2,s3,r,h,g,xi,yj; m,n,a,b,c,d
h=(b-a)/n;
g=(d-c)/m; ba
r=(f(a,c)+f(a,d)+f(b,c)+f(b,d))/4; h
s1=0; n

for (i=1;i<=n-1;i++) d c
{ g
m
xi=a+i*h;
s1=s1+f(xi,c)+f(xi,d);
}
s2=0;
r
1
 f (a, c)  f (a, d )  f (b, c)  f (b, d )
4

for (j=1;j<=m-1;j++)
{ s1=0
yj=c+j*g;
s2=s2+f(a,yj)+f(b,yj);
} i=1
s3=0;
for (i=1;i<=n-1;i++)
{ xi=a+ih
xi=a+i*h;

for (j=1;j<=m-1;j++) s2=s2+f(xi,c)+f(xi,d)


{
yj=c+j*g;
s3=s3+f(xi,yj); i=i+1
}
} Po
T=h*g*(r+(s1+s2)/2+s3); i≤n-1
cout << "Vlera e integralit T="<< T<< "\n";
return 0; A
}

Dalja:

Vlera e integralit T=0.0408994


Bazat e gjuhës programuese C++ S. Bekteshi 75

Jo

S
h
 f (a)  f (b)  4s1  2s2 
3

s1=s1+f[a+(2n-1)h]

Fundi
Bazat e gjuhës programuese C++ S. Bekteshi 76

7. Matricat

Matricat njëdimensionale

Matrica është një grup i lokacioneve të memorjes të njëpasnjëshme çdonjëra prej tyre
përmbanë të dhëna të të njejtit tip dhe të njejtit emër. Çdo lokaciom i memorjes quhet element i
matricës. Çdo lokacioni të posaqëm të memorjes respektivisht çdo elementi të matricës i çasemi me
emrin e matricës të shoqëruar me numrin e pozitës të elementit të caktuar në kllapat e mesme ( [] )

Shembull: Në fig është është paraqitur matrica me emrin c. Kjo matricë i ka 12 elemente. Çdo
elementi mund ti drejtohemi me emrin e matricës së shoqëruar me numrin e pozitës të elementit të
caktuar në kllapat e mesme ([ ]). Numrimi i elementeve të matricës fillon nga zero kështuqë
elementi i parë në çdo matricë është elementi zero. Në rastin tonë elementi i parë është c[0]
elementi i dytë është elementi c[1] e kështu me radhë. Elementi i njëmbëdhjetë është c[10] dhe
elementi i dymbëdhjetë është c[11].

Numrimi i elementeve të matricës fillon nga zero kështu që elementi i parë në çdo matricë
është elementi zero [0]. Elementi i n-të i matricës është [n-1]. Për emra të matricave vlejnë të
njejtat konventa si edhe për ndryshoret tjera.
Numri i pozitës i cili gjendet brenda kllapave të mesme quhet edhe indeks. Indeksi pra është
numri i elementeve të matricës i futur brenda kllapave të mesme Indeksi duhet të jetë një numër i
plotë ose një shprehje që jep numër të plotë. Nëse programi e përdorë një shprehje si indeks atëhere
shprehja zhvillohet në përcaktimin e indeksit.

Shembull: Nëse supozojmë se a është e barabartë me 5 dhe b është e barabartë me 6 atëhere


urdhëresa:
c[a+b]+=2;
ia shton 2 elementit të matricës c[11]
Nëse c[0] e ka vlerën 15 ndërsa c[11] e ka vlerën 8 atëhere që ta shtypim shumën e këtyre
elementeve shkruajmë:
cout<<c[0]+c[1]<<end1;
ose nëse dëshirojmë që elementin e dytë ta pjestojmë me 2 dhe rezultati i fituar ti jipet x
shkruajmë:
x=c[1]/2;

Kllapat e mesme që përdoren për kufizimin e indeksave të një matrice në të vërtetë janë
operatorë në C++. Prioriteti i kllapave të mesme është i njejtë si edhe i kllapave të vogla (tabela)

Deklarimi i matricës

Matricat zejnë vend në memorje. Deklarimi i një matrice bëhet duke e shkruar tipin, emrin e
matricës dhe indeksin.
tipi emri_vargut[indeksi];
Shembull: Kompajllerit i themi ti rezervoj 12 elemente për matricën me emër matrica1 të tipit long
int me deklaratën:
long matrica1[12];
Bazat e gjuhës programuese C++ S. Bekteshi 77

Pasi që çdo long int kërkon 4 bajt atëhere kompajlleri rezervon gjithsejt 48 bajt të
njëpasnjëshëm të memorjes. Në një deklaratë memorja mund të rezervohet edhe për disa matrica:
int matrica1[12], matrica2[22] matrica3[112];

Matricat mund të deklarohen ashtu që të përmbajnë edhe tipe tjera të të dhënave.

Inicializimi i matricës

Inicializimi i matricës mund të bëhet me rastin e deklarimit të saj pas emrit të matricës
shkruhet shenja e barazimit (=) dhe brenda kllapave të mesme shënohen vlerat me radhë të ndara
me presje.

Shembull: int Matrica1[5] = { 10, 20, 30, 40, 50 };


deklaron matricës Matrica1 me 5 numra të plotë. Elementit të parë të Matrica1[0] i jipet vlera 10,
elementit të dytë të Matrica1[1] i jipet vlera 20 e kështu me radhë.

Nuk lejohet asesi që të inicializohen më shumë elemente se sa janë deklaruar ndërsa lejohet
që numri i elementeve të deklaruar të jetë më i madh se numri i vlerave të inicializuara Nëse
nevojitet kompajlleri mund të llogarit madhësinë e një matrice (Prg10)

Shembull: Nuk lejohet asesi që të inicializohen më shumë elemente se sa janë deklaruar si psh:
int Matrica1[5] = { 10, 20, 30, 40, 50, 60 };
Në këtë rast kompajlleri do të tregoj për gabim sepse në Matrica1 janë deklaruar 5 elemente
ndërsa janë inicializuar 6 vlera. Lejohet që numri i elementeve të deklaruar të jetë më i madh se
numri i vlerave të inicializuara psh:
int Matrica1[10] = { 10, 20, 30, 40, 50 };
sepse elementet që nuk inicializohen i marrin vlerën 0.
Plotësisht matricë e njejtë krijohet edhe nëse nuk shënohet numri i elementeve brenda
kllapave të mesme:
int Matrica1[] = { 10, 20, 30, 40, 50 };

Nëse nevojitet kompajlleri mund të llogarit madhësinë e një matrice.

Shembull: const USHORT gjatesiaVargu1;


Matrica1 = sizeof(Matrica1)/sizeof(gjatesiaMatrica1[0]);
e vendos USHORT ndryshoren Matrica1 në rezultatin që fitohet me pjestimin e gjatësisë së tërë
matricës me gjatësinë e çdo shënim individual në matricë.

1: //Prg. 10 – Përdorimi i një matricë integer


2: #include <iostream.h>
3:
4: int main()
5: {
6: int Matrica1[5];
7: int i;
8: for ( i=0; i<5; i++) // 0-4
9: {
10: cout << "Vlerat per Matrica1[" << i << "]: ";
11: cin >> Matrica1[i];
Bazat e gjuhës programuese C++ S. Bekteshi 78

12: }
13: for (i = 0; i<5; i++)
14: cout << i << ": " << Matrica1[i] << "\n";
15: return 0;
16: }
Dalja: Vlera per Matrica1[0]: 3
Vlera per Matrica1[1]: 6
Vlera per Matrica1[2]: 9
Vlera per Matrica1[3]: 12
Vlera per Matrica1[4]: 15
0: 3
1: 6
2: 9
3: 12
4: 15

Klasifikimi i matricave

Klasifikimi i të dhënave ( dmth vendosja e të dhënave sipas rregullave të caktuara siç është
zmadhimi ose zvoglimi) është njëra nga zbatimet më të rëndësishme të llogaritjes. Shqyrtjmë rastin
e klasifikimit të vlerave të matricës në formën e zmadhimit (prg13).
Teknika e klasifikimit të fluskave ose klasifikimit të fundosjes sepse vlerat e vogla
gradualisht „si fluska“ ngjiten lartë deri në maje të matricës ashtu si ngriten lartë fluskat në ujë
ndërsa përderisa vlerat e mëdha bijnë në fund të matricës kjo teknikë duhet të kaloj disa herë nëpër
matricë. Gjatë çdo kalimi krahasohen çiftet suksesive të elementeve. Nëse çifti është në formën e
rritjes (ose vlerat janë identike) vlerat lihen ashtu siç janë. Nëse çifti është në formë të zvoglimit ato
shkëmbehen (i ndërrojnë vendet ndërmjet veti).
Së pari krahasohet elementi i parë i matricës me elementin e dytë të matricës pastaj
elementii dytë me elementin e tretë, elementi i tretë me të katërtin e kështu me radhë deri sa të
kompletohet kalimi me krahasimin e e elementit të parafundit me elementin e fundit të matricës.
Nëse janë n elemente të matricës atëhere kryhen vetëm n -1 krahasime. Pasi bëhet krahasimi në
mënyrë suksesive, vlera e madhe nënjë kalim për disa pozita zbret poshtë përderisa vlera e vogël
mund të ngritet lartë vetëm për një pozitë. Në kalimin e parë me siguri vlera më e madhe do të zbres
në elementin e fundit të matricës. Në kalimin e dytë, vlera e dytë për nga madhësia zbret në
elementin n-1. Në kalimin e n-1, vlera e n-1 për nga madhësia me siguri zbret në elementin e dytë.
Vlera më e vogël mbetet në elementin e parë kështu që për n elemente nevoiten n-1 kalime.
E metë e kësaj teknike është sepse ekzekutohet shumë ngadal e kjo vjen në shprehje
posaqërisht tek matricat e mëdha. Natyrisht ekzistojnë edhe teknika tjera të klasifikimit.

1. // prg13 Klasifikimi i vlerave të varut në formën rritëse


2.
3. #include <iostream.h>
4. #include <iomanip.h>
5.
6. int main()
7. {
8. const int elemente = 10;
9. int a[ elemente ] = { 2, 6, 4, 8, 10, 12, 89, 68, 45, 37 };
10. int i, mbaje;
Bazat e gjuhës programuese C++ S. Bekteshi 79

11. cout << "Vlerat e matrices në forme origjinale \n";


12. for ( i = 0; i < elemente; i++ )
13. cout << setw( 4 ) << a[ i ];
14. for ( int kalime = 0; kalime < elemente - 1; kalime++ ) // kalimet
15.
16. for ( i = 0; i < elemente - 1; i++ ) // një kalim
17.
18. if ( a[ i ] > a[ i + 1 ] ) { // nje krahasim
19. mbaje = a[ i ]; // nje shkembim
20. a[ i ] = a[ i + 1 ];
21. a[ i + 1 ] = mbaje;
22. }
23. cout << "\ Vlerat e matricës në formë rritese \n";
24.
25. for ( i = 0; i < elemente; i++ )
26. cout << setw( 4 ) << a[ i ];
27. cout << endl;
28. return 0;
29. }

Analizë: Programi i mësipërm i klasifikon vlerat e matricës prej 10 elementeve në formën e


zmadhimit. Kjo arrihet në këtë mënyrë: së pari e krahason a[0] me a[1] pastaj a[1] me a[2], a[2] me
a[3] e kështu me radhë deri sa të kompletohet kalimi me krahasimin e a[8] me a[9]. Edhe pse janë
10 elemente kryhen vetëm 9 krahasime. Pasi bëhet krahasimi në mënyrë suksesive, vlera e madhe
nënjë kalim për disa pozita zbret poshtë përderisa vlera e vogël mund të ngritet lartë vetëm për një
pozitë. Në kalimin e parë me siguri vlera më e madhe do të zbres në elementin e fundit të matricës
a[9]. Në kalimin e dytë, vlera e dytë për nga madhësia me siguri zbret në elementin a[8]. Në
kalimin e nëntë, vlera e nëntë për nga madhësia me siguri zbret në elementin a[1]. Vlera më e vogël
mbetet në a[0] kështu që për 10 elemete nevoiten 9 kalime.
Klasifikimi bëhet me ciklin for. Nëse shkëmbimi është i domosdoshëm ai kryhet në formën:
mbaje = a[i];
a[i]= a[i+1];
a[i+1] = mbaje;
ku ndryshorja mbaje përkohsisht e ruan njërën nga të dy vlerat që janë shkëmbyer. Shkëmbimi nuk
mund të kryhet vetëm me:
a[i]= a[i+1];
a[i+1] = a[i];
sepse nëse a[i] është 5 ndërsa a[i+1] është 7 pas dhënjes së parë të vlerave të dy vlerat do të jenë 5
ndërsa 7 do të humbet prandaj nevoitet ndryshorja mbaje

Matricat dhe funksionet

Bartja e një argumenti të matricës në funksion bëhet duke e shkruar emrin e matricës pa
kllapa.

Shembull: Nëse deklarohet matrica:


int Matrica1[5]
urdhëresa për funksionin thirrës
temperatura(Matrica, 5);
Bazat e gjuhës programuese C++ S. Bekteshi 80

e bart matricën Matrica1 dhe madhësinë e tij në funksionin temperatura

Matricat shumëdimensionale

Matricat mund të kenë më shumë se një dimension. Çdo dimension paraqitet me një indeks
në matricë. Pra matrica dydimensionale i ka dy indekse, matrica tredimesnionale i ka tre indekse e
kështu me radhë.

Inicializimi i matricave shumëdimensionale

Prej matricave shumëdimensionale më së shumti përdoret matrica dydimensionale [i][j] ku


indeksi i parë ([i]) paraqet rreshtat ndërsa indeksi i dytë ([j]) kolonat (prg11). Si shembëll më i
përshtatshëm i matricës dydimensionale janë tabelat respektivisht matricat.

Shembëll: Matrica 3x5 deklarohet:


int matrica[3][5];
në të cilën pesë elementet e para të indeksit të dytë shkojnë në matrica[0], pesë elementet e dyta të
indeksit të dytë shkojnë në matrica[1] e kështu me radhë. Inicializimi bëhet në formën:
int matrica[3][5]=(1,2,3,4,5,6,7,8,9,10,11,12,13,14,15);
Në mënyrë më të qartë mund të paraqitet nëpërmes kllapave:
int matrica[3][5]=( (1, 2, 3, 4, 5),
(6, 7, 8, 9, 10),
(11,12,13,14,15) );
sepse kompajlleri i injoron kllapat e brendshme.

//Prg.11 Krijini i matricës dydimensionale


1: #include <iostream.h>
2: int main()
3: {
4: int matrica[5][2] = { {0,0}, {1,2}, {2,4}, {3,6}, {4,8}};
5: for (int i = 0; i<5; i++)
6: for (int j=0; j<2; j++)
7: {
8: cout << "matrica[" << i << "][" << j << "]: ";
9: cout << matrica[i][j]<< endl;
10: }
11:
12: return 0;
13: }

dalja:
matrica[0][0]: 0
matrica[0][1]: 0
matrica[1][0]: 1
matrica[1][1]: 2
matrica[2][0]: 2
matrica[2][1]: 4
matrica[3][0]: 3
Bazat e gjuhës programuese C++ S. Bekteshi 81

matrica[3][1]: 6
matrica[4][0]: 4
matrica[4][1]: 8

Analizë: Rreshti 4 e deklaron matrica një matricë dydimensionale. Dimensioni i parë i ka pesë
numra të plotë ndërsa dimensioni i dytë nga dy numra të plotë. Kjo formon matricën 5x2. Vlerat
inicializohen në çifte. Në rreshtat 5 dhe 6 formohet cikli for. Cikli i jashtëm for kalon nëpër secilin
anëtar të dimensionit të parë. Për çdo anëtarë të atij dimensioni cikli i brendshëm for kalon nëpër
çdo anëtarë të dimensionit të dytë. Kjo është në përputhje me daljen matrica[0][0] shoqërohet nga
matrica[0][1]. Dimensioni i parë inkrementohet vetëm pasi dimensioni i dytë është inkrementuar
me 1. Pasta dimensioni i dytë fillon përsëri.

Çdo vlerë duhet të ndahet me presje pa marrë parasysh kllapat. Në fund vendoset pikëpresje
(prg12).

1 // prg12 Shembull i matricës dydimensioanle


2
3 #include <iostream.h>
4 #include <iomanip.h>
5
6 const int studentet = 3; // numri i studenteve
7 const int testimet = 4; // numri i testimeve
8
9 int minimum( int [][ testimet ], int, int );
10 int maximum(int [][ testimet ], int, int );
11 float mesatare( int [], int );
12 void rezultati( int [][ testimet ], int, int );
13
14 int main()
15 {
16 int NotatStudent[ studentet ][ testimet ] =
17 { { 77, 68, 86, 73 },
18 { 96, 87, 89, 78 },
19 { 70, 90, 86, 81 } };
20
21 cout << "Matrica eshte:\n";
22 rezultati( NotatStudent, studentet, testimet );
23 cout << "\n\n nota me e vogel: "
24 << minimum( NotatStudent, studentet, testimet )
25 << "\n nota me e madhe: "
26 << maximum( NotatStudent, studentet, testimet ) << '\n';
27
28 for ( int person = 0; person < studentet; person++ )
29 cout << "Nota mesatare per student " << person << " eshte "
30 << setiosflags( ios::fixed | ios::showpoint )
31 << setprecision( 2 )
32 << mesatare( NotatStudent[ person ], testimet ) << endl;
33
34 return 0;
35 }
Bazat e gjuhës programuese C++ S. Bekteshi 82

36
37 // Gjen noten minimale
38 int minimum( int notat[][ testimet ], int nxenesit, int testimet )
39 {
40 int Notavogel = 100;
41
42 for ( int i = 0; i < nxenesit; i++ )
43
44 for ( int j = 0; j < testimet; j++ )
45
46 if ( notat[ i ][ j ] < Notavogel )
47 Notavogel = notat[ i ][ j ];
48
49 return Notavogel;
50 }
51
52 // Gjen noten maksimale
53 int maximum( int notat[][ testimet ], int nxenesit, int testimet )
54 {
55 int Notamadhe = 0;
56
57 for ( int i = 0; i < nxenesit; i++ )
58
59 for ( int j = 0; j < testimet; j++ )
60
61 if ( notat[ i ][ j ] > Notamadhe )
62 Notamadhe = notat[ i ][ j ];
63
64 return Notamadhe;
65 }
66
67 // Percakton noten mesatare per secilin student
68 float mesatare( int setOfNotat[], int testimet )
69 {
70 int totali = 0;
71
72 for ( int i = 0; i < testimet; i++ )
73 total += setOfNotat[ i ];
74
75 return ( float ) totali / testimet;
76 }
77
78 // Shtyp matricën
79 void rezultati( int notat[][ testimet ], int nxenesit, int testimet )
80 {
81 cout << " [0] [1] [2] [3]";
82
83 for ( int i = 0; i < nxenesit; i++ ) {
84 cout << "\nNotatStudent[" << i << "] ";
85
Bazat e gjuhës programuese C++ S. Bekteshi 83

86 for ( int j = 0; j < testimet; j++ )


87 cout << setiosflags( ios::left ) << setw( 5 )
88 << notat[ i ][ j ];
89 }
90 }

Shumë manipulime me matrica e përdorin strukturën përsëritëse for

Shembull: Struktura vijuese for i jep vlera 0 çdo elementi të rreshtit të tretë të matrica1:
for (kolona=0; kolona<4; kolona++)
matrica1[2][kolona]=0;
Ne përcaktuam rreshtin e tretë sepse ne e dijmë se indeksi i parë është gjithëmonë 2 (0 është
indeksi i parë i rreshtit ndërsa 1 është indeksi i dytë i rreshtit). Cikli for e ndryshon vetëm indeksin e
dytë ( pra indeksin e kolomës). Struktura e mëparshme është ekuivalente me:
matrica1[2][0]=0;
matrica1[2][1]=0;
matrica1[2][2]=0;
matrica1[2][3]=0;
ose
Shembull: Struktura e përfshirë vijuese e përcakton totalin e të gjitha elementeve në matricën
matrica1:
Totali=0;
for (rreshti=0; rreshti<3; rreshti++)
for (kolona=0; kolona<4; kolona++)
Totali+= matrica1[rreshti][kolona];
Struktura for i mbledh elementet e matricës për secilën herë nga një rresht. Struktura e
jashtme for fillon me dhënjen e vlerave rreshti (pra indeksit të rreshtit) nga 0 ashtu që
elemetet e rreshtit të parë të mund të totaled nga struktura e brendshme for. Struktura e jashtme
for pastaj e inkrementon rreshti në 1 ashtu që rreshti i dytë të mund të mblidhet. Pastaj
struktura e jashtme for e inkrementon rreshti në 2 ashtu që rreshti i tretë të mund të
mblidhet. Rezultati shtypet kur përfundon struktura for.
Bazat e gjuhës programuese C++ S. Bekteshi 84

8. Treguesit

Në këtë kapitull shqyrtohen treguesit (ang. pointers) në gjuhën C++. Yreguesi është njëra
prej mjeteve më të fuqishme që është në dispozicion të programeve C++ me të cilën manipulohet në
mënyrë të drejtëpërdrejtë memorja e kompjuterit. Për të kuptuar më mirë treguesit në Shtesën1.
është sqaruar edhe pak memorja RAM.

Ruajtja e adresës në tregues

Çdo ndryshore e ka adresën e vet. Adresat mund të ruhen në tregues. Treguesit janë
ndryshore. Për ta vlejnë të gjitha rregullat kryesore si edhe për ndryshoret tjera. Pra edhe ndryshoret
e tipit tregues duhet të deklarohen para se të përdoren. Dallimi i vetëm qëndron në të dhënat të cilat
ata i mbajnë. Treguesit nuk përmbajnë të dhëna në kuptimin e zakonshëm të fjalës. Ata përmbajnë
adresat e të dhënave. Në gjuhën C++ kemi dy operatorë treguesit.
& operatori ”adresa e “
* operatori i indireksionit
Operatorët * dhe & janë inverz njëri ndaj tjetrit.
Treguesit janë njëri nga tipet e rrjedhura të gjuhës C++. Edhe pse shumë programe në
njëfarë mënyre i implementojnë treguesit, kjo në gjuhën C++ është më elegante dhe më e fuqishme

Deklarimi i treguesve

Treguesi është ndryshore që e ruan adresën e memorjes si vlerë të tij. Natyrisht vdryshoret
drejtëpërsëdrejti përmbajnë vlera të caktuara Treguesi në anën tjetër përmbam një adresë të një
ndryshoreje që përmban një vlerë të caktuar. Në këtë mënyrë ndyshorja drejtëpërsëdrejti i referohet
një vlere ndërsa treguesi në mënyrë të tërthortë i referohet një vlere fig. Referimi i një vlere
nëpërmes treguesit quhet indireksion. Deklarimi i treguesve përfshinë element të ri – operatorin e
indireksionit *. Ja forma e përgjithshme :
tipi * emri _treg
komponenta tip e specifikon tipin e të dhënave në të cilat tregohet ndërsa emri_treg është
identifikatori më të cilin emrohet treguesi. Deklaratën mund t’a lexoni lehtë nëse shkoni në kahje të
kundërt - ‘emri_treg është tregues në objektin e tipit int”.Treguesit mund të deklarohen ashtu që të
tregojnë në objektet e çfardo tipi të të dhënave. Treguesi duhet gjithësesi të inicializohet. Nëse nuk
dini se me çka t’a inicializoni treguesin atëhere jepni vlerën zero. Kjo që thamë më lartë më mirë
kuptohet në bazë të progarmit Prg.33.

1. //prg.33
2. #include <iostream.h>
3. #include <conio.h>
4.
5. main ()
6. {
7. int ndrysh=100 ;
8. int*tndrysh;
Bazat e gjuhës programuese C++ S. Bekteshi 85

9.
10. cout<<"Numri eshte:"<< ndrysh ;
11. cout<<"\n Adresa e ndryshores ndrysh eshte: "<<&ndrysh;
12.
13. tndrysh=&ndrysh;
14. cout<<"\n *tndrysh eshte: "<<*tndrysh;
15. cout<<"\n Lokacioni i tndrysh eshte: "<< tndrysh;
16. getch();
17. return 0;
18. }
Dalja: Numri eshte: 100
Adresa e ndryshores ndrysh eshte: 0x0012ff88
*tndrysh eshte: 100
Lokacioni i tndrysh eshte: 0x0012ff88

Analizë: Të marrim një shembull të treguesit në ndryshore të tipit int që në mënyrë më detale të
shqyrtojmë deklarimin e treguesve
int ndrysh =100 ;
Të supozohet se dëshironi të deklaroni një ndryshore të tipit tregues. Kjo ndryshore e tipit tregues
nuk do mbaj vlerën e ndryshores ndrysh por do t’ju tregon (drejton) në ndryshoren ndrysh. siç është
ilustruar në fig.12 Fakti se përkthyesi i C++ e ka ruajtur ndryshoren ndrysh të themi në adresën
0x0012ff88. Që të deklaroni ndryshoren e tipit Adresat Memorja
tregues tndrysh veprohet:
int *tndrysh: ndrysh në
e cila mundson që në mënyrë indirekte t’i 0x0012ff88 100 tndrysh dërgon
afrohemi vlerës së ndryshores ndrysh. Karakteri në ndrysh
tndrysh në
yll * e deklaron ndryshoren tndrysh si tregues 0x0012ff88
0x0012ff88
ndërsa tipi int që ndryshorja tndrysh është
tregues në ndryshoren më numër të plotë. Dmth
kombinimi int* e deklaron ndryshoren tndrysh
Fig.12 Paraqitja skematike e memorjes
të tipit “tregues në tipin int” dhe tregon se në
program do të shfrytëzohet për afrimin në mënyrë indirekte të ndryshores së numrit të plotë .
Nëse x është ndryshore e çfardo tipi atëhere vlera e shprehjes &x është adresa x. Vlera e
shprehjes &x mund t’i jipet ndryshores e cila është e deklaruar si tregues në tip të njejtë siç është x.
Përndryshe edhe tndrysh mund të shkruhet urdhëresa:
int *tndrysh=&ndrysh;
e cila ndryshores tndrysh i jipet adresa e ndryshores ndrysh .
Pra, ndryshorja ndrysh është deklaruar si ndryshore e tipit int dhe është inicializuar me
vlerën 100, tndrysh është deklaruar si tregues në vlerën e tipit int – është inicializuar me adresën e
ndryshores ndrysh; tndrysh është tregues. Adresa të cilën tndrysh e ruan është adresa e ndryshores
ndrysh. vlera në adresën të cilën tndrysh e ruan është 100.
Vërejmë se adresa e ndrysh është e njejtë me vlerën e tndrysh në dalje që vërteton se adresa
e ndrysh me të vërtetë i është dhënë ndryshores të tipit tregues tndrysh.

Operatori i adresës

Operatori & - quhet operatori i adresës është një operator unar i cili kthen adresën e
operandit të tij.
Bazat e gjuhës programuese C++ S. Bekteshi 86

Shembull: Psh: int y =5;


int *ty;
urdhëresa
ty=&y;
i jep adresën e ndryshores y ndryshores të tipit tregues ty.

Fig treguesin në memorje duke supozuar se ndryshorja e tipit int është ruajtur në lokacionin
0x0012ff88 ndërsa ndryshorja e tipit tregues tndrysh është ruajtur në lakozcionin e memorjes
0x0012ff88. operandi i operatorit të adresës duhet me qenë një tndrysh (diçka në të cilën vlera
mund ti jipet siç është emri i ndryshores). Operatori i adresës nuk mund të zbatohet në konstante, në
shprehje të cilat nuk rezultojnë me references ose ndryshoret që deklarohen me klasën register.

Operatori i indireksionit

Operatori i indireksionit (operatori yll *) quhet gjithashtu edhe operator i dereferencimit.


Indireksioni dmth çasja e vlerës nëpërmes adresës e cila ruhet në tregues. Treguesi mundson që në
mënyrë indirekte të fitohet vlera e cila ruhet në atë adresë. Kur treguesi dereferencohet, kthehet
vlera në adresë e cila ruhet në tregues. Ndryshoret e zakonshme kanë çasje të drejtëpërdrejtë në
vlerat e veta :

Shembull: nt x; , x = y:

Treguesit kanë çasje indirekte të vlerës së ndryshores, adresën e së cilës e ruan.

Shembull: Që t’ia jepni vlerën nga matja1 ndryshores së re në matja2 duke shfrytëzuar treguesin
tmatja duhet që
:int matja1;
int matja;
matja = *tmatja;
Operatori i indireksionit (*) para ndryshores tmatja dmth “ mirre vlerën e cila ruhet në
adresën e ndryshores tmatja dhe jipja ndryshores matja”.

Shprehjet dhe aritmetika me ndryshore të tipit tregues

Shtrohet pyetja se operatorët a mund të kenë tregues si operandë dhe nëse po si përdoren
ata. Treguesit janë operand valid në shprehjet aritmetikore, shprehjet për dhënjen e vlerave dhe
shprehjet krahasuese; Megjithate të gjithë operatorët që përdoren në këto shprehje natyrisht se nuk
janë të xalid me ndryshoret e tipit tregues.
Një grup i vogël i operacioneve aritmetike mund të kryhen në tregues. Treguesi mund të
inkrementohet (++) dhe të dekrementohet (- -), një integer mund ti shtohet treguesit (+ ose +=), një
integer mund të zbritet nga treguesi (- ose -=) ose një tregues mund të zbritet nga treguesi tjetër.

Sqarim: Në matematikën e zakonshme 3000 + 2 = 3002. një gjë e tillë nuk vlen në matematikën e
treguesve. Kur një integer i shtohet ose i zbritet një treguesi atëhere treguesi nuk rritet ose
zvoglohet për atë integer por me integer herë madhësia e objektit të cilit i referohet treguesi. Numri
i bajtëve varet nga tipi i të dhënave të objektit. Psh urdhëresa :
tvlera +=2;
Bazat e gjuhës programuese C++ S. Bekteshi 87

do të jep 3008 (3000+2*4) nëse një integer është ruatur në 4 bajt të memorjes.
Nëse treguesi rritet për një atëhere operatori i inkrementimit (++) dhe dekrementimit (- -)
mund të përdoren. Urdhëresat tvlera++; si edhe ++tvlera; e rritin treguesn që tregon në lokacionin e
ardhshëm të matricës. Urdhëresat tvlera- -; si edhe - -tvlera; e zvoglojnë treguesin që tregon në
lokacionin e mëparshëm të matricës.
Ndryshoret e tipit tregues mund të zbriten njëra nga tjetra. Psh nëse tvlera1 e përmban
lokacionin 3000 ndërsa tvlera2 e përmban vlerën 3008 atëhere urdhëresa:
x=tvlera1 – tvlera2:
x do ti jep vlerën 2.

Nëse matrica është deklaruar me të dhëna të tipeve të ndryshme, urdhëresa që vjen do ta rrit
treguesin për dyfishin e numrit të bajtëve që nevoiten për ruajtjen e një objekti të atij tipi të të
dhënave. Kur e kryejmë matematikën me tregues në vargun e karaktereve rezultatet do të jenë
konsistente me matematikën e zakonshme sepse madhësia e karaktereve është 1 bajt.
Aritmetika me trergues është e pakuptimtë përveç në rastin kur kryhet me një matricë. Ne
nuk mund të supozojmë se dy ndryshore të të njejtit tipi ruhen në mënyrë kontinuale (afër njëri
tjetri) në memorje përveç rastit kur ata janë elemente fqinj (afër njëri tjetrit) të një matrice.
Një treguesi mund ti jipet vlera e treguesit tjetër nëse ata të dytë janë të të njejtit tip. Në
rastet tjera duhet të përdoret operatori cast për të kthyer vlerat e treguesit në të djadhtë të operatorit
për dhënjen e vlerave në treguesin e tipit majtas operatorit për dhënjen e vlerave. Përjashtim nga kjo
rregullë është treguesi në void (pra void*) që është një tregues gjenerues që mund të paraqes çfardo
tipi të treguesve. Çfardo tipi i treguesve mund të jetë oid pa e përdor operatorin cast.
Treguesi void* nuk mund të dereferencohet sepse kompajlleri duhet të dij tipin e të dhënave
që të përcaktoj numrin e bajtëve që duhet dereferencuar për secilin tregues. Në rastin e treguesit në
void numri i bajtëve nuk mund të përcaktohet nga tipi i të dhënave.
Treguesit mund të krahasohen duke i përdor operatorët për krahasim dhe operatorin e
barazimit. Krahasimet e tila janë të pakuptimta përveç për treguesit që tregojnë në anëtarët e të të
njejtës matrica sepse kemi të bëjmë me krahasimin e adresave që ruhen në tregues.

Marrëdhënja në mes të matricave dhe treguesve

Treguesit dhe matricat kanë lidhje të ngushtë në C++. Emri i një matrice mund të mendohet
si një tregues konstant. Treguesit mund të përdoren për kryerjen e çfardo operacioni duke përfshi
edhe indeksimin.

Shembull: Të supozojmë se matrica e tipit int b[5] dhe ndryshorja integer e tipit tregues tb janë
deklaruar më parë. Pasi emri i matricës (pa indeks) është tregues në elementin e parë të matricës ne
mund të vendosim tb në adresën e elementit të parë të matricës b me urdhëresën:
tb = b;
kjo është ekuivalente me marrjen e adresës së elementit të parë si vijon:
tb = &b[0];
Elementit të matricës b[3] mund ti çasemi me shprehjen treguesore:
*(tb+3);
në shprehjen e mësipërme 3 është offset në tregues. Kur treguesi tregon në fillimin e një matrice
offset tregon se cilit element të matricës i çasemi dhe se vlera offset është identike me indeksin. Ku
notacion quhet notacioni treguesoffset. Kllapat janë të domosdoshme për shkak të prioriteti i
operatorit * është më i madh se i +.
Treguesit mund të indeksohen si edhe matricat. Për shembull shprehja:
tb[1];
Bazat e gjuhës programuese C++ S. Bekteshi 88

i referohet elementit të matricës b[1], Ky quhet notacioni tregues/indeks.

Treguesit në funksione

Treguesi në funksion përmban në memorje adresën e funksionit. Më parë treguam se emri i


matricës me të vërtetë është adresa në memorje e elementit të parë të matricës. Në mënyrë të
ngjashme emri i funksionit në të vërtetë është adresa startuese në memorje e kodit që kryen detyrën
e funksionit. Treguesit në funksione mund të thirren nga funksionet, mund të kthehen nga
funksionet dhe të ruhen në matrica.
Bazat e gjuhës programuese C++ S. Bekteshi 89

9. Stringjet

Karakteret janë elementet themelore të ndërtimit të programit burimor të C++. Çdo program
është i kompozuar si sekuencë e karaktereve – të cilat janë kuptimplote si tërësi – që interpretohen
nga kompjuteri si vargje të instruksionve që përdoren për kryerjen e ndonjë detyre. Një program
mund të përmbaj konstante të karaktereve. Konstanta e karakterit është një vlerë integer që paraqitet
si karakter në thojza të njëfishta. Vlera e karakterit konstant është vlera integer e karakterit në
grupin e karaktereve të makinës. Psh „x“ paraqet vlerën integer të x (122 në grupin e karaktereve
ASCII).
Stringu është varg i karaktereve i cili trajtohet si një njësi e vetme. Një string mund të
përmbaj shkronja, numra dhe karaktere speciale. Konstantet string në C++ shkruhen në thojza të
dyfishta.

Shembull: „Agron Berisha“


„ 38000 Mitrovicë“
„ 028-234.567“

Një string në C++ është një varg i karaktereve që mbaron me karakterin null (\0). Një
stringu i çasemi nëpërmes treguesit në karakterin e parë të stringut. Vlera e një stringu është adresa
(konstantë) e karakterit të tij të parë. Kështu në C++ është më e saktë të thuhet se stringu është një
tregues konstantë – në fakt tregues në karakterin e parë të stringut. Në këtë mënyrë stringjet janë të
ngjashme me matricat sepse emri i matricës është gjithashtu tregues (konstant) në elementin e tij të
parë.
Stringu mund të inicializohet në një deklaratë ose në matricë të karaktereve ose në
ndryshore të tipit char*.

Shembull: Secila nga deklaratat:


char ngjyra[] = „ kuqe“;
char *tngjyra = „kuqe“;
e inicializon ndryshoren në string „ kuqe“. Deklarata e parë e formon një matricë ngjyra me 5
elemente që përmban karakteret ‚k’, ‚u’,’q’,’e’ dhe ‚\0’. Deklarata e dytë formon një ndryshore të
tipit tregues tngjyra e cila tregon në stringun „kuqe“ diku në memorie.

Stringu mund ti jipet një matrice duke përdor fuksionin cin.

Shembull: Urdhëresa vijuese mund të përdoret që stringu ti jipet matrica e karaktereve:


fjala[20]
cin>>fjala;
Stringu i cili shtypet nga shfrytëzuesi ruhet në fjala. Urdhëresa e mësipërme i lexon
karakteret përderisa të has në hapësirë (blank), tab, rreshti i ri ose në indikator mbarim-i-fajllit. Të
përkujtojmë se stringu nuk guxon të jetë më i gjatë se 19 karaktere duke rezervuar për karakterin
null për përfundim.

Nganjëherë është e nevojshme që të futet i tërë rreshti në matricë. Për këtë qëllim në C++
kemi funksionin cin.getline. Funksioni cin.getline i ka tri argumente - vargu i karaktereve në të cilin
ruhet rreshti i tekstit, gjatësia dhe karakteri përkufizues.
Bazat e gjuhës programuese C++ S. Bekteshi 90

Shembull: Segmenti i programit:


char fjalia[80];
cin.getline(fjalia, 80, „\0“);
e deklaron matricën fjalia me 80 karaktere e pastaj e lexon rreshtin e tekstit nga tastatura në
matricë. Funksioni e ndal leximin e karaktereve posa të has në „\n“, në indikatorin mbarimi-i-fajllit
ose kur numri i karaktereve të lexuara është për një më pak se gjatësia e theksuar në argumentin e
dytë (karakteri i fundit në matricë rezervohet për karakterin null të mbarimit). Argumenti i tretë „\n“
është vlerë e n[nkuptuar (default), prandaj deklarata e dytë mund të shkruhet edhe në formën:
cin.getline(fjalia, 80);
Bazat e gjuhës programuese C++ S. Bekteshi 91

10. Klasa

Tipi i ri bëhet me deklarimin e klasës. Klasa është një grup i ndryshoreve, shpesh të tipeve
të ndryshme të cilat janë të kombinuara me tërësinë e funksioneve të lidhura mes vete. Klasa mund
të përbëhet nga çfardo kombinimi i tipeve të ndryshoreve dhe tipeve të klasave tjera. Ndryshoret që
i përmban klasa paraqesin ndryshoret (të dhënat) anëtarë. Ndryshoret anëtarë janë pra pjesë e
klasës. Funksionet anëtarë (metodat) në klasë zakonisht manipulojnë me ndryshoret anëtarë.
Funksionet anëtarë janë pjesë e klasës njësoj si edhe ndryshoret anëtarë. Mostra individuale e klasës
është objekti. Funksionet anëtarë përcaktojnë se çka mund të kryejnë objektet e klasës. Nga kjo që u
tha më lartë rrjedh se klasat i mundësojnë programuesit të modelojnë objektet të cilat kanë veti (që
paraqiten nëpërmes të dhënave anëtarë) dhe sjelljeve (që paraqiten nëpërmes funksioneve anëtarë).

Deklarimi i klasës

Deklarimi i klasës bëhet duke përdor fjalën e rezervuar class e shoqëruar me emrin e klasës
çiftit të klapave të mëdha {} brenda të cilave gjenden të dhënat anëtarë dhe funksionet anëtarë të
klasës. Deklarimi i klasës përfundon me pikëpresje. Sintaksa për klasën është si vijon:

class emri_klases
{
// këtu vijnë fjalët e rezervuara për kontrollin e çasjes
// këtu vijnë ndryshoret e deklaruara dhe metodat e deklaruara të klasës
};

Deklarimi i klasës përmbanë deklaratat e të dhënave anëtarë të klasës dhe funksioneve


anëtarë të klasës. Deklarata e të dhënave anëtarë të klasës janë prototipet e funksioneve. Funksionet
anëtarë mund të definohen brenda klasës por praktikë e mirë programuese është që të definohen
jasht klasës. Deklarimi i klasës nuk rezervon memorie Deklarimi i paraqet përkthyesit se sa është
klasa e madhe d.m.th. se çfarë hapësire përkthyesi duhet të rezervoj për çdo klasë e cila formohet.

Shembull: class Grupi


{
unsigned int NumStudent; // është ndryshore anëtarë
unsigned int Viti; // është ndryshore anëtarë
mesatarja(); // është funksion (metodë) anëtarë
};
Fizika. NumStudent=15;
Fizika. Viti=4;
Fizika. mesatarja()

Deklarimi gjithashtu vetëm i paraqet përkthyesit se çka është klasa, cilat të dhëna i përmban
(NumStudent, Viti) dhe çka mund të bëjë deklarimi mesatarja().
Në këtë rast nëse vlera e plotë (int) ka dy bajt, Klasa i ka 4 bajt (të dy ndryshoret nga dy).
mesatarja() nuk zen hapësirë sepse kurrfarë hapësire depozituese nuk rezervohet për funksionet
(metodat) anëtarë prg14.
Bazat e gjuhës programuese C++ S. Bekteshi 92

1: // Prg14 Deklarimi i klasës dhe definimi i një objekti të klasës


2: // çasja anëtarëve public
3:
4: #include <iostream.h> // për cout
5:
6: class Grupi
7: {
8: public: // Anëtarët në vazhdim janë public
9: int NumStudent;
10: int Viti;
11: };
12:
13:
14: void main()
15: {
16: Grupi Fizika;
17: Fizika.NumStudent = 15; // I jipet vlera ndryshores anëtar
18: cout << "Grupi Fizika ka -" ;
19: cout << Fizika.NumStudent << " student.\n";
20:
Dalja: Grupi Fizika ka -15 student.

Analizë: Deklarimi i klasës bëhet duke përdor fjalën e rezervuar class (rreshti 6)e shoqëruar me
emrin e klasës (Grupi) çiftit të kllapave të mëdha {}(reshti 7 dhe 11) brenda të cilave gjenden të
dhënat anëtarë Numstudent (rreshti 9) dhe Viti (rreshti 10). Deklarimi i klasës përfundon me
pikëpresje (rreshti11).
Në rreshtin 14 fillon funksioni main. Fizika është deklaruar si objekt i klasës Grupi në
rreshtin 16. Numri i studentëve të Fizikës është dhënë me 15 në rreshtin 17. Në rrshtat 18 dhe 19
ndryshorja Numstudent është pëdor për të shtypur njoftiin për Fizikën.
Rreshti 8 përmban fjalën e rezervuar public, e cila tregon se çdo gjë që pason është publike deri
te fjala e rezervuar private ose mbarimi i deklaratës së klasës.
Emri i klasës bëhet përcaktues i tipit të ri. Mund të kemi disa objekte në klasë ashtu si mund
të kemi disa ndryshore psh të tipit int. Programuesi mund të krijoj tipe të reja të klasës sipas
nevojës. Kjo është arsyeja pse thuhet se C++ është një gjuhë e cila mund të zgjërohet

Definimi i objektit

Objekti definohet ashtu siç definohet çdo ndryshore.

Shembull: unsigned int numStudenti; // definimi i ndryshores Studenti


Grupi Fizika; // definimi i klasës
Më sipër është definuar objekti Fizika klasa (tipi) e të cilit është Grupi

Definimi i objakteve bëhet që të bëhet dallimi ndërmjet klasës si ide dhe klasës së caktuar që
ne n’a intereson (Fizika). D.m.th. objekti është mostër individuale e klasës. Një klasë (psh Grupi)
mund të ketë një ose më shumë objekte (Fizika, Kimia,…)
Bazat e gjuhës programuese C++ S. Bekteshi 93

Çasja e anëtarëve të klasës

Pasi të definohet objekti (p.sh. Fizika) me anë të operatorit pikë (.) bëhet çasja në anëtarët e
atij objekti, prg14).

Shembull: Fizika. NumStudent = 15;


Në të njejtën mënyrë që të thirret fonksioni mesatarja() duhet që:
Fizika. mesatarja ();

Kur shfrytëzohen metodat e klasës ato thirren. Në këtë rast është thirrë funksioni
mesatarja() për objektin Fizika.
Duhet theksuar se vlerat iu jipen objekteve e jo klasave ashtu si iu jipen vlerat ndryshoreve e
jo tipeve.

Shembull:
Nuk iu jipen vlera tipit të të dhënave:
int=5; //gabim Grupi NumStudent=15; //gabim
por ndryshoreve
int x; //mirë Grupi Fizika; //mirë
x=5; //mirë Fizika. NumStudent=15; //mirë

Zakonisht programuesit e rinj gabojnë kur thirrin funksionet të cilat nuk janë deklaruar në
klasë, p.sh.
class. Grupi; class. Grupi;
Grupi Fizika; gabim mesatarja (); mirë
Fizika. mesatarja (); Grupi Fizika;
mesatarja ();

Përdorimi i fjalëve të rezervuara public dhe private

Specifikuesit për çasje të anëtarëve (public oe private) mbarojnë me dy pika (:) dhe mund të
paraqiten në definicionin e klasës shumë herë dhe në çfardo renditje.Të gjithë anëtarët e klasës, të
dhënat dhe metodat të cilat nuk deklarohen (si public) nënkupton se janë private. Anëtarëve private
mund t’i çasemi vetëm brenda metodave (funksioneve) të së njejtës klasë. Anëtarëve public mund
t’i çasemi nëpërmjet të çdo objekti të klasës.

Shembull:
class Grupi class Grupi
{ { public
unsigned int NumStudent; unsigned int NumStudent;
unsigned int Viti; unsigned int Viti;
mesatarja (); mesatarja ();
}; gabim }; mirë
Grupi Fizika; Grupi. Fizika;
Fizika. NumStudent=15; Fizika. NumStudent=15;
Fizika. Viti=4; Fizika. Viti=4;
Fizika. mesatarja(); Fizika. mesatarja()
Bazat e gjuhës programuese C++ S. Bekteshi 94

Duhet theksuar se është gabim pasi Fizika nuk ka çasje në ndryshoret NumStudent, Viti dhe
mesatarja() edhepse Fizika është objekt i klasës Grupi. Më parë kemi theksuar se të dhënat
konsiderohen private përveç nëse deklarohen si public. Nëse dëshirojë që Fizika të ketë çasje në
ndryshoret NumStudent, Viti dhe Mesatarja() atëhere duhet të përdoret fjala e rezervuar public
(si në rastin mirë).

Të dhënat anëtarë natyrisht vargisen në pjesën private të klasës dhe funksionet anëtarë
natyrisht vargisen në pjesën public të klasës. E lumdërta është e pazakonshme dhe konsiderohet si
praktikë e dobët programuese
Theksuam se si rregullë e përgjithshme është që të dhënat anëtarë të ruhen si private. Për
këtë arsye duhet të formohen funksione public të njohura si funksione çasëse për vendosjen dhe
marrjen e ndryshoreve private. Këto funksione çasëse janë funksionet anëtarë të cilat thirren nga
pjesët tjera të programit me qëllim që t’I fitojnë dhe vendosin ndryshoret private prg15 .

1. // Prg15 Deklarimi i klasës Grupi. Të dhënat anëtarë janë private


2. // Metodat çasëse public ndërmjetsojnë në dhënjen ose marrjen të të dhënave private
3.
4.
5. class Grupi
6. {
7. public:
8. // Funksionet çasëse public
9. unsigned int MerrViti();
10. void VenViti(unsigned int Niti);
11.
12. unsigned int MerrDrejtimi();
13. void VenDrejtimi(unsigned int Drejtimi);
14.
15. // Funksioni anëtar public
16. mesatarja();
17.
18. // Të dhënat anëtarë private
19. private:
20. unsigned int Viti;
21. unsigned int Drejtimi;
22.
23. };

Analizë: Kjo klasë ka 5 metoda public. Rreshtat 9 dhe 10 përmbajnë funksionet çasëse për Viti.
Rreshtat 13 she 14 përmbajnë metodat çasëse për Drejtimi. Këto funksione çasëse i vendosin (i
japin) ndryshoret anëtarë dhe i kthejnë vlerat e tyre. Funksioni anëtar public mesatarja() është
deklaruar në rreshtin 16. mesatarja() nuk është funksion çasës. Ai as nuk merr e as nuk jep
ndryshore anëtarë, ai kryen shërbime tjera për klasën por psh e shtyp fjalën mesatarja. Të dhënat
anëtarë hanë deklaruar në rreshtat 20 dhe 21. Që të vendosni vitin e Fizikës duhet ta jipni vlerën
metodës PerVite() si vijon:
Grupi Fizika;
Fizika.PerVite(2); // E ven vitin e Fizikës duke përdor funksionin çasës public
Bazat e gjuhës programuese C++ S. Bekteshi 95

Implementimi i metodës së klasës

Theksuam më parë se funksioni çasës siguron interfejs public për të dhënat anëtarë private
të klasës. Implementim quhet definimi i funksionit. Definimi i funksionit anëtarë fillon me emrin e
klasës pas së cilës vjen dy pika të dyfishta, emri i funksionit dhe parametrat e tij. (prg16)

1: // Prg16 Implementimi i metodave të klasës


2:
3:
4: #include <iostream.h> // për cout
5:
6: class Cat // fillon deklarimi i klasës
7: {
8: public: // fillon pjesa publike
9: int MerrViti(); // funksion çasës
10: void VenViti (int Viti); // funksion çasës
11: void mesatarja(); // funksion i përgjithshëm
12: private: // fillon pjesa private
13: int vitiI; // ndryshorja anëtar
14: };
15:
16: // MerrViti, funksion çasës public
17: // e kthen vlerën e anëtarit VitiI
18: int Grupi::MerrViti()
19: {
20: return VitiI;
21: }
22:
23: // Definicioni i VenViti, public
24: // funksion çasës
25: // e kthen anëtarin e vendosur VitiI
26: void Cat::VenViti(int Viti)
27: {
28: // E ven ndryshoren anëtar VitiI
29: // në vlerën e dhënë nga parametri Viti
30: VitiI = Viti;
31: }
32:
33: // Definicioni i metodës mesatarja
34: // kthen: void
35: // parametera: Asnjë
36: // akcion: Shtyp "mesatarja" në ekran
37: void Cat::mesatarja()
38: {
39: cout << "mesatarja.\n";
40: }
41:
42: // Formon Grupi, e ven vitin, e ka mesataren
43: //, na tregon për vitin, mesatareja përsër
44: int main()
Bazat e gjuhës programuese C++ S. Bekteshi 96

45: {
46: Grupi Fizika;
47: Fizika.VenViti(2);
48: Fizika.mesatarja();
49: cout << "Grupi i Fizikës per vitin e - " ;
50: cout << Fizika.MerrViti() << " ka 15 studente \n";
51: Fizika.mesatarja();
52; return 0;
53: }
Dalja: mesatarja.
Grupi i Fizikës per vitin e – 2 ka 15 studente
mesatarja.

Analizë: Definicioni i klassës Grupi bëhet në rreshtat 6-14 contain the definition of the Cat class.
Rreshti 8 përmbanë public, i cili i tregon kompajllerit se në vazhdi ka të bëjë me anëtarë publik.
Në rreshtin 9 deklarohet funksion çasës MerrViti().MerrViti () mundëson çasjen në
ndryshoren anëtar privat VitiI, i cili është deklaruar në rreshtin 13.
Rreshti 10 ka funksionin çasës publik VenViti().VenViti() pranon një integer si një
argument dhe ven VitiI në vlerën e atij argumenti.
Në rreshtin 11 deklarohet metoda e klasës mesatarja().mesatarja () inuk është funksion
çasës. Këtu ai është një metodë e përgjiyhshme që shtyp fjalën mesatarja në ekran.
Rreshti 12 fillon pjesa private, e cila përfshin vetëm deklaratën në rreshtin e 13 të ndryshores
anëtar privat VitiI. Deklarimi i klasës përfundon me mbylljen e kllapës dhe pikëpresje në rreshtin
14.
Rreshtat 18-21 përmbajnë defiimin e funksionit anëtar MerrViti(). Kjo metodë nuk pranon
parametar, ajo kthen një integer. Të theksojë se metodat e klasës përmbajnë emrin e klasës të
shoqëruar me dy parë dypika. Dhe emri i funksionit (rreshti 18). Kjo sintaksë i tregon kompallerit
se funksioni MerrViti() function që definohet këtu është njëri që është deklaruar në klasën
Grupi. Me përjashtimin e këtij rreshti kryesues funksioni NerrViti() krijohet si çdo funksion
tjetër.
Funksioni NerrViti() i necoitet vetëm një rresht; ai kthen vlerën në VitiI. Të theksojmë se
funksioni main() nuk mund ti çaset VitiI sepse VitiI është privat në klasën Grupi.
Funksioni main main() ka çasje në metodën publike NerrViti() sepse NerrViti() ëdhtë
funksion anëtar i klasës Grupi, ai ka çasje të plotë në ndryshoren VitiI. Kjo çashe i mundëson
NerrViti () të kthej vlerën e VitiI në main().
Rreshti 26 përmban definimin e funksionit anëtar VenViti(). Ai pranon një parametrë integer
dhe e ven vlerën e VitiI në vlerën e atij parametri në rreshtin 30 sepse ai është anëtar i klasës
Grupi. VenViti()ka çasje direkte në ndryshoren anëtar VitiI.
Në rreshtin 37 fillon definimi ose implementimi i metodës mesatarja() të klasës Grupi. Ai
është funksion i një rreshti që shtyp fjalën mesatarja në ekran. Të përkujtojmë se karakteri \n
shtyp rreshtin e ri në ekran.
Në rreshtin 44 fillon trupi i programitme funksionin e njohur main() Në këtë rast ai nuk ka
argumente dhe kthen void. Në rreshtin 46, main() deklaron një Grupi që quhet Fizika. Në
rrestin 47, vlera 5 i jipet ndryshores anëtar VitiI me metodën çasëse VenViti(). Të
theksojmë se metoda thirret duke e përdor emrin e klasës (Fizika) i shoqëeuar nga operatori
anëtar (.) dhe emri i metodës (VenViti()). Në të njejtën mënyrë mund të thirrençdo metodë
tjetër në klasë.
Bazat e gjuhës programuese C++ S. Bekteshi 97

Në rreshtin 48 thirret funksioni anëtar mesatarja() dhe rreshti 49 shtyp njoftiminduke e përdor
funksionin çasës MerrViti() . Rreshti 51 e thirr përsëri mesataraja().

Konstruktorët dhe destruktorët

Ekzistojnë dy mënyra për inicializimin e ndryshoreve:

Shembull: int viti; dhe int viti = 4;


Viti = 4;

Si të inicializohen të dhënat anëtarë të klasës?


Klasa e ka funksionin special anëtarë të quajtur konstruktor. Të theksojmë se funksioni
anëtar me të njejtin emër si edhe klasa quhet konstruktor i asaj klase. Konstruktori është funksion i
posaqëm anëtar që i inicializon të dhënat anëtarë të objektit të klasës. Funksioni konstruktor i klasës
quhet automatikisht kur formohet një objekt i asaj klase. Më vonë do të shohim se është e
zakonshme të kemi disa konstruktorë për një klasë. Të theksojmë se konstruktori mund të pranoj
parametra sipas nevojës por nuk mund të ketë vlerë që kthen e bile as void.. Të dhënat anëtarë nuk
mund të inicializohen kur gjenden në trupin e klasës. Këto të dhënat anëtarë duhet të inicializohen
nga konstruktori i klasës ose mund ti jepen vlera me funksionin “vendose”. Kur të deklarohet
konstruktori deklarohet edhe destruktori. Ashtu siç konstruktorët formojnë dhe i inicializojnë
objektet e klasës, destruktorët pastrojnë për objektin dhe e lirojnë memorien
Destruktori gjithmonë e ka emrin e klasës të cilit i paraprin tilda. (~). Destruktorët nuk ka
argumente nuk kanë vlerë që kthejnë. Prandaj deklarimi i klasës psh Grupi përfshinë:
-Grupi ( );

Konstruktorët dhe destruktorët default

Nëse në program nuk është deklaruar konstruktori ose destruktori, kompajlleri do ta formoj
një në vend të juaj. Konstruktori dhe destruktori default nuk pranojnë argumente dhe nuk bëjnë
asgjë. çfarë të mire kemi nga konstruktori i cili nuk bën asgjë? Pjesërisht kjo është çështje e formës.
Të gjitha objektet duhet të konstruktohen dhe destruktohen dhe këto funksione që nuk bëjnë asgjë
thirren në kohën e duhur.

Sqarim: Megjithate, deklarimi i një objekti pa parametra si:


Grupi Kimia; // Kimia nuk pranon argumente
ju duhet të keni konstruktorin në formën
Grupi();

Kur të definohet një objekt i klasës thirret konstruktori. Konstruktori mund të mos ketë
parametra, ta ketë një ose më shumë parametra.

Shembull: Nëse konstruktori Grupi ka dy parametra ju mund të definoni objektin e Grupi si vijon:
Grupi Fizika (5,7);
Nëse konstruktori pranon një parametër:
Grupi Fizika (5);
Në rastin kur konstruktori nuk pranon parametra atëhere e lini pa kllapa:
Grupi Fizika ;
Bazat e gjuhës programuese C++ S. Bekteshi 98

Në rastin kur konstruktori nuk pranon parametra atëhere duhet të lihet pa kllapa. Ky është
një përjashtim nga rregulla e cila thotë se të gjitha funksionet duhet të kenë kllapa bile edhe nëse
nuk kanë parametra.

Sqarim: Për këtë arsye ne jemi në gjendje të shkruajmë:


Grupi Fizika;
e cila eshtë thirrje në konstruktorin default.

Nuk është e thënë që të përdoret konstruktori default të formuar nga kompajlleri. Ju


mundeni gjithëmonë të shkruani konstruktorin e juaj pa parametra. Bile edhe konstruktorët pa
parametra mund të kenë trupin e funksionit në të cilin ata i inicializojnë objektet e tyre ose kryejnë
punë tjera.
Nëse e deklaroni konstruktorin deklaroni edhe destruktorin (vetëm sa për ta ruajtur formën)
edhe nëse ai destruktor nuk kryen asgjë. Edhepse është e vërtetë se destruktori default punon në
mënyrë më korrekte nuk ka asgjë të keqe ta deklaroni tuajin. Ai e bën kodin e juaj më të qartë
Prg17 .

1: // Prg17. Deklarimi i konstruktorëve dhe destruktorëne


2:
3:
4: #include <iostream.h> // për cout
5:
6: class Fizila // fillon deklarimi i klasës
7: {
8: public: // fillon pjesa publike
9: Grupi(int FillimViti); // Konstruktori
10: ~Grupi(); // Destruktori
11: int MerrViti(); // funksion çasës
12: void VenViti(int Viti); // funksion çasës
13: void mesatarja();
14: private: // fillon pjesa private
15: int VitiI; // ndryshore anëtar
16: };
17:
18: // konstruktori i Grupi,
19: Grupi::Grupi(int FillimViti)
20: {
21: VitiI = FillimViti;
22: }
23:
24: Grupi::~Grupi() // destruktori, nuk kryen asnjë aksion
25: {
26: }
27:
28: // MerrViti, funksion çasës public
29: // kthen vlerën e anëtarit VitiI
30: int Grupi::MerrViti()
31: {
32: return VitiI;
33: }
Bazat e gjuhës programuese C++ S. Bekteshi 99

34:
35: // Definimi i VenViti, funksion çasës public
37:
38: void Grupi::VenViti(int Viti)
39: {
40: // Even ndryshoren anëtar VitiI në vlerën e
41: // e vendosur nga parametri Viti
42: VitiI = Viti;
43: }
44:
45: // Definimi i metodës mesatarja
46: // kthen void
47: // parameterat: Ska
48: // veprimi: Shtyp mesatarja në ekran
49: void Grupi::mesatarja()
50: {
51: cout << "mesatarja.\n";
52: }
54: // Formon grupi, e ven VitiI, ka mesatarja
55 // na tregon VitiI përsëri e tregon mesatarja.
56: int main()
57: {
58: Grupi Fizika(5);
59: Fizika.mesatarja();
60: cout << ""Grupi i Fizikës per vitin e - " ;
61: cout << Fizika.MerrViti() << " ka 15 studente \n";
62: Fizika.mesatarja();
63: Fizika.VenViti(7);
64: cout << " Fizika në vitin- - " ;
65: cout << Fizika.MerrViti() << " ka 14 studentë.\n";
66; return 0;
67: }
Dalja: mesatarja.
Grupi i Fizikës per vitin e - 5 ka 15 studente
mesatarja.
Fizika në vitin- 7 ka 14 studentë.

Analizë: Programi Prg17 është i njejtë me programin Prg16 përveçse në rreshtin 9 ia shton
konstruktorin i cili pranon një integer.
Rreshti 10 deklaron destruktorin, i cili ska parametra. Destruktorët kurrë nuk kanë
argumente, dhe kurrë as konstruktori e as destruktori nuk kthejnë vlera – nuk kthejnë as void.
Rreshtat 19-22 paraqesin implementimin e konstruktorit. Është e ngjashme me
implementimin e funksionit çasës VenViti(). Këtu nuk kemi vlerë kthyese value.
Rreshtat 24-26 paraqesin implementimin e destruktorit ~Grupi(). Ky funksion nuk kryen
asgjë,por duhet të përfshihet definimii funksionit nëse është deklaruar në deklarimin e klasës.
Rreshti 58 përmban definimin e objektit Fizika. të Grupi Vlera 5 është bartur në
konstruktorin Fizika. Nuk ka nevoj të thorretl VenViti(), sepse Fizika ishte krijuar me vlerën
5 në ndryshoren e tij VitiI, siç është paraqitur në rreshtin 61.
Në rreshtin 63, VitiI i Fizikës iu është ridhënë vlera tani në 7.
Rreshti 65 shtyp vlerën e re.
Bazat e gjuhës programuese C++ S. Bekteshi 100

Ndarja e interfejsit nga implementimi

Klasat e thjeshtojnë programimin sepse klientët (klientët janë pjesë të programit të cilat
krijojnë dhe i përdorin objektet e klasës) duhet të mirren vetëm me operacionet që gjenden në
objekt. Operacionet e tilla janë të dizajnuara që më shumë të jenë të orientuara kah klienti se sa të
orientuara kah implementimi. Klienti nuk duhet të ketë lidhje me implementimin e klasës (edhepse
klienti natyrisht dëshiron implementim korrekt dhe efikas). Interfejsi ndryshohet por shumë më
rrallë se sa implementimi. Kur një implementim ndryshohet në pajtueshmëri me atë duhet të
ndryshohet edhe kodi i varur nga implementimi. Me fshehjen e implementimit ne e eliminojmë
mundësinë që pjesët tjera të programit të bëhen të varura nga detalet e implementimit të klasës.
Njëra prej parimeve themelore të ingjinieringut të mirë softuerik ëahtë ndarja e interfejsit
nga implementimi. Kjo e bën më të lehtë modifikimin e programit.
Në të vërtetë fajllat header duhet të përmbajnë disa pjesë të implementimit dhe
paralajmërime për disa pjesë tjera të implementimit.

Përfundim:

Fjala e rezervuar class përdoret për të deklaruar tipe të reja. Klasa është koleksion i të
dhënave të cilët mund të jenë të tipeve të ndryshme duke përfshirë edhe klasa të tjera. Klasa
gjithashtu përmban funksionet e klasës ose metodat – ato janë funksione të cilat shfrytëzohen për
manipulimin me të dhënat në klasë dhe për kryerjen e shërbimeve tjera për klasën.
Objektet definohen si të tipit të ri në të njejtën mënyrë si definohen ndryshoret. Duhet të
theksohet tipi (klasa) e pastaj emri i ndryshores (objekti). Anëtarët dhe funksionet e klasës I çasemi
me operatorin pikë (*).
Fjalët e rezervuara për kontrollën e çasjes shfrytëzohen për deklarimin e seksionit të klasës
si është private. Secila fjalë e rezervuar e ndryshon kontrollën e çasjes nga ajo pikë (ku deklarohet)
deri në fund të klasës ose deri të fjala tjetër e rezervuar për kontroll të çasjes. Deklarimi i klasës
mbaron me mbylljen e kllapës së madhe dhe shenjën pikëpresje.
Metoda public e çasjes është funksioni anëtar i klasës i cili shfrytëzohet për ruajtjen e vlerës
së ndryshores private ose vendosjen e vlerës së saj.
Bazat e gjuhës programuese C++ S. Bekteshi 101

Programimi i orientuar në objekte.

Tani do të fillojmë me orientimin në objekte në C++. Ne do të shohim se orientimi në


objekte është është mënyra e natyrshme e të menduarit mbi botën dhe për shkruarjen e programeve
të kompjuterit. Ne do të analizojmë një problem tipik, urdhëresat që kërkojnë të ndërtohet një
sistem, të përcaktojmë se çfarë klasa nevoiten për implementimin e sistemit, të përcaktojmë se cilat
atribute nevoitet ti kenë objektet e këtyre klasave, të përcaktojmë se çfarë sjelljesh objektet duhet të
kryejnë dhe të përcaktojmë se si objektet duhet të bashkëveprojnë njeri me tjetrin në mënyrë që të
përmbushen qëllimet e përgjithshme të sistemit.
POO i bashkon të dhënat (atributet) dhe funksionet (sjelljet) në forma të cilat quhen
objekte;. Funksionet dhe të dhënat janë të lidhura ngusht njëra me tjetrën. Objektet e kanë vetinë e
fshehjes së informatave. Kjo dmth se edhepse objektet mund të dijnë se si të komunikojmë njërio
me tjetrin nëpërmes interfejsit të qartë objektet natyrisht se nuk lejon të dijnë se si implementohen
objektet tjera; detalet e implementimit janë të fshehura brenda vetë objekteve.
Njerzit dijnë për objektet duke studjuar atributet e tyre dhe duke vrojtuar sjelljet e tyre.
Objekte të ndryshme kanë veti dhe sjellje të ngjashme.
Programimi i oreientuar në objekte (POO) i modelon objektet e botës reale me homologje
softuerike. Përparsia është se raportet e klasës ku objektet e të njejtës klasë i kanë karakteristikat e
njejta. POO na jep mënyrën më të natyrshme dhe intuitive që të përcjellim procesin e programimit
dmth me modelimin e objekteve të botës reale me atributet dhe me sjelljet e tyre. POO gjithasht
modelon edhe komunikimin në mes të objekteve.

Në C dhe gjuhët tjera programuese proceduriale programimi tenton të jetë programim i


orientuar në aksione përderisa në C++ programim i orientuar në objekte. Në C njësia e programimit
është funksioni ndërsa në C++ njësia e programimit është klasa prej së cilës krijohen objektet. Klasa
e C++ përmban funksione.
Programuesit e C koncentrohen në shkruarjen e funksioneve. Funksionet përmbajnë grupe të
aksioneve të cilat kryejnë detyra të zakonshme. Disa funksionee e formojnë programin. Detyra
parësore e të dhënave është të ndihmojnë aksionet të cilat i kryejnë funksionet.
Programuesit e C koncentrohen në formimin e tipeve të definuara nga shfrytëzuesi që quhen
klasa. Çdo klasë përmbanë të dhëna dhe funksione të cilat manipulojnë me të shënat. Komponenetet
e të dhënave të klasës quhen të dhënat anëtarë. Komponenetet e funksioneve të klasës quhen
funksone anëtarë (ose metoda në gjuhët tjera programuese të orientuara në objekte). Ashtu si për
shembëll në tipet e ndëruara që më parë si psh int quhet ndryshore edhe në tipin e definuar nga
shfrytëzuesi (pra klasa) quhet objekt. Programuesi i përdorë tipet e definuara që më parë për
formimin e tipeve të definuara nga shfrytëzuesi. Fokusi i vëmendjes së C++ është në klasa (jashtë të
cilave ne i ndërtojmë objektet) më shumë se në funksione.
Klasa është si një projekt shtëpi. Jashtë projektit ndërtohet shtëpia dhe jashtë klasës
ndërtohen objktet. Një projekt shtëpie mund të përdoret për ndërtimin e disa shtëpive.
Klasa në C++ është një evolucion natyror i strukturave në C.
Bazat e gjuhës programuese C++ S. Bekteshi 102

Klasat i mundësonë programuesit të modeloj objekte që kanë atribute (të paraqitura si të


dhëna anëtarë) dhe sjellje ose operacione (të paraqitura si funksione anëtarë). Tipet që përmbajnë të
dhënat anëtarë dhe funksionet anëtarë definohen në C++ duke përdorë fjalën e rezervuar class.
Pasi të definohet klasa emri i klasës mund të përdoret për deklarimin e objekteve të asaj klase.
class Koha {
public:
Koha();
void jepeKoha( int, int, int );
void shtypUshtarake();
void shtyptStandarde();
private:
int ora; // 0 - 23
int minuti; // 0 - 59
int sekonda; // 0 - 59
};
Definicioni i klasës Koha fillon me fjalën e rezervuar class. Trupi i klasës kufizohet me
kllapat e mëdha ({dhe}). Definicioni i klasës ndërpritet me pikëpresje. Definicioni i klasës Koha
përmbanë tre anëtarë: ora, minuti dhe sekonda
Specifikuesit për çasje të anëtarëve public dhe private. Çasja për çdo funksion anëtar ose të
dhënë anëtarë e deklaruar pas specifikuesit për çasje të anëtarëve public (dhe para specifikuesit
të ardhshëm për çasje të anëtarëve) është e mundshme kudo që programi ka çasje në një objekt
të klasës Koha. Çasja për çdo funksion anëtar ose të dhënë anëtarë e deklaruar pas specifikuesit
për çasje të anëtarëve private (dhe deri te specifikuesi i ardhshëm për çasje të anëtarëve) është e
mundshme vetëm për funksionet anëtarë të klasës. Specifikuesit për çasje të anëtarëve mbarojnë
me dy pika (:) dhe mund të paraqiten në definicionin e klasës shumë herë dhe në çfardo renditje.
Definicioni i klasës përmbanë prototipet për katër funksionet anëtarë pas specifikuesit për çasje
të anëtarëve public: Koha(), jepeKoha( int, int, int ), shtypUshtarake(), shtyptStandarde(). Këto
janë funksionet anëtarë public të klasës (ose: shërbimet public, sjelljet public, interfejsi i klasës).
Këto fuksione do të përdoren nga klientët (pjesë të programit që janë shfrytëzues) e klasës për të
manipuluar me të dhënat e klasës.
Të theksojmë se funksioni anëtar me të njejtin emër si edhe klasa quhet funksioni
konstruktor i asaj klase. Konstruktori është funksion i posaqëm anëtar që i inicializon të dhënat
anëtarë të objektit të klasës. Funksioni konstruktor i klasës quhet automatikisht kur formohet një
objekt i asaj klase. Më vonë do të shohim se është e zakonshme të kemi disa konstruktorë për
një klasë. Të theksojmë se nuk është përcaktuar tipi kthyes për konstruktorin.
Pas specifikuesit për çasje të anëtarëve private paraqiten tre anëtarë integer. Kjo tregon se
mund ti çasemi këtyre të dhënave anëtarë të klasës vetëm nga funksionet anëtarë ose siç do të
shohmi më vonë nga „shokët“ e klasës. Kështu mund ti çasemi të dhënave anëtarë nëpërmes
katër funksioneve prototipet e tp cilave janë paraqitë në definicionin e klasës )ose nëpërmes
„shokëve“ të klasës). Të dhënat anëtarë natyrisht vargisen në pjesën private të klasës dhe
funksionet anëtarë natyrisht vargisen në pjesën pulic të klasës. E lumdërta është e pazakonshme
dhe konsiderohet si praktikë e dobët programuese.
Njëherë kur të definohet klasa mund të përdoret si tip në deklaratat si vijon:
Koha përëndimi{/ /objekt i tipit Koha
Vargu jashtKohës[5]; //varg i objekteve Koha
*treguesiNëKohë //tregues në objektin e Koha
&mbrëmja=përëndimi; //referenca në objektin e Koha
Bazat e gjuhës programuese C++ S. Bekteshi 103

Emri i klasës bëhet përcaktues i tipit të ri. Nund të kemi disa objekte në klasë ashtu si mund
të kemi disa ndryshore psh të tipit int. Programuesi mund të krijoj tipe të reja të klasës sipas
nevojës. Kjo është arsyeja pse thuhet se C++ është një gjuhë e cila mund të zgjërohet.
(Shembulli11)
Të theksojmë se të dhënat anëtarë nuk mund të inicializohen kur gjenden në trupin e klasës.
Këto të dhënat anëtarë duhet të inicializohen nga konstruktori i klasës ose mund ti jepen vlera me
funksionin “vendose”.
Funksioni me të njejtin emër si edhe klasa të cilit i paraprin karakteri tildë (~) quhet
destruktor i asaj klase (ky shembull nuk e përmbanë në mënyrë eksplicite destruktorin). Destruktori
nuk ka argimente prandaj edhe nuk mund të përgjithsohet.
Funksionet public i implementojnë sjelljet ose shërbimet që klasa iu jep klientëve të saj – të
cilave iu referohemi si interfejsi i klasës ose interfejsi public).
Definicioni i klasës përmbanë deklaratat e të dhënave anëtarë të klasës dhe funksioneve
anëtarë të klasës. Deklarata e të dhënave anëtarë të klasës janë prototipet e funksioneve. Funksionet
anëtarë mund të definohen brenda klasës por praktikë e mirë programuese është që të definohen
jasht klasës.
Të theksojmë se operatori binar i rezulucionti të fushëveprimit (::) binary scope resolution
operator. Në shembullin e mësipërmë çdo definicion i funksionit anëtarë është i përcjellur nga
definicioni i klasës. Posa të definohet klasa dhe të deklarohen funksonet anëtarë të saj funksionet
anëtarë duhet të definohen. Çdo funksion anëtarë i klasës mund të definohet drejpërsëdrejti në
trupin e klasës (më mirë se sa të përfshiihen nprototipet e funksionit në klasë) ose funksionet
anëtarë mund të definohen jashtë trupit të klasës. Kur të definohet funksioni anëtarë pas definimit të
klasës përkatëse emrit të funksionit i paraprin emri i klasës dhe operatori (::). Pasi klasat e
ndryshme mund të kenë të njejtat emra anëtarë operatori :: i lidhë emrat anëtarë me emrin e klasës
në mënyrë të njëvlershme të identifikoj funksionet anëtarë të klasës së veqantë. Bile edhe nëse
funksioni anëtarë i deklaruar në definicionin e klasës mund të definohet jashtë definicionit të klasës.
Funksioni i tillë është akoma brenda fushëveprimit të klasës dmth emri i tij njihet vetëm nga
anëtarët tjerë të klasës përveç nëse i referohemi drejt një objekti të klasës, referencës në një objekt
të klasës ose treguesit në një objekt të klasës.
Të sqarojmë shkurtimisht mbi fushëveprimin e klasës. Nëse funksioni anëtarë është i
definuar në definicionin e klasës funksioni anëtarë automatikisht është në formën inline. Mbani
mend se kompajlleri mban të drejtën që të mos inline asnjë funksion.
Është interesant se funksionet anëtarë shtypUshtarake dhe shtypStandarde nuk kanë
argumente. Kjo është për arsye se funksionet anëtarë në mënyrë implicite e dijnë se duhet ti shtypin
të dhënat anëtarë të objektit Koha të veqant. Kjo i bën funksionet anëtarë thirrës më konciz se sa
funksionet thirrëse të zakoshme në programimin procedural.
Klasat e thjeshtojnë programimin sepse klientët (shfrytëzuesit e objektit të klasës) duhet të
mirren vetëm me operacionet që gjenden në objekt. Operacionet e tilla janë të dizajnuara që më
shumë të jenë të orientuara kah klienti se sa të orientuara kah implementimi. Klienti nuk duhet të
ketë lidhje me implementimin e klasës (edhepse klienti natyrisht dëshiron implementim korrekt dhe
efikas). Interfejsi ndryshohet por shumë më rrallë se sa implementimi. Kur një implementim
ndryshohet në pajtueshmëri me atë duhet të ndryshohet edhe kodi i varur nga implementimi. Me
fshehjen e implementimit ne e eliminojmë mundësinë që pjesët tjera të programit të bëhen të varura
nga detalet e implementimit të klasës.
Shpesh klasë nuk duhet krijuar “prej rastit”. Ato mund të fitohen prej klasëve tjera që japin
atribute dhe sjellje që klasa e re mund ti përdor. Ose klasat mund të përmbajnë objekte të klasave
tjera si anëtarë të tyre. Një softuer i tillë e rrit produktivitetin e programuesit. Krijimi i klasave të
reja nga klasat ekzistuese quhet trashëgimi. Përfshiraja e objekteve të klasës si anëtarë të klasëve
tjera quhet kompozim. Për trashëgiminë dhe kompozimin do të diskutojmë edhe më vonë.
Bazat e gjuhës programuese C++ S. Bekteshi 104

Zakonisht mendohet se në programimin e orientuar në objekte, objektet duhet tëjenëtë


mëdha pasi ato përmbajnë të dhëna dhe funksione. Lgjikisht kjo është e vërtetë sepse programuesit
duhet të mendojnë për objekte që përmbajnë të dhëna dhe funksone. Praktikisht kjo nuk është e
vërtetë.

Fushëveprimi i klasës dhe çasja në anëtarët e klasës

Të dhënat anëtarë të klasës (ndryshoret e deklaruara në definicionin e klasës) dhe funksionet


anëtarë (funksionet e deklaruara në definicionin e klasës) i takojnë fushëveprimit të klasës.
Funksonet joantarë janë të definuara në fuhsëveprimin e fajllit.
Brenda fushëveprimit të klasës, anëtarët e klasës drejpërsëdrejti janë të çasshëm nga të
gjithë funksonet anëtarë të klasës dhe mund të referohen sipas emrit. Jasht fushëveprimit të klasës
anëtarët e klasës referohen nëpërmes njërës nga mundësitë e një objekti – një emri të një objekti,
referencës së një objekti ose treguesit në një objekt. Më vonë do të hohim se një mundësi futet nga
kompajlleri në çdo referencë të të dhënave anëtarë ose funksioni anëtarë të një objekti.
Funksionet anëtarë të një klase mund të përgjithsohen por vetëm me funksionet anëtarë
tjerë të klasës. Përgjithsimi i funksionit anëtarë thjesht jep në definicionin e klasës një prototip për
çdo verzion të funksionit të përgjithsuar dhe jep një definicion të veqant të funksionit për çdo
verzion të funksionit.
Funksionet anëtarë kanë fushëveprimin e funksionit në klasë - ndryshoret e definuara në
funksionin anëtarë njihen vetëm nga ai funksion. Nëse një funksion anëtarë e definon një ndryshore
me të njejtin emër si një ndryshore me fushëveprim të klasës, ndryshoruja me fushëveprim të klasës
fshieht nga ndryshorja me fushëveprim të funksionit. Një ndryshoreje të tillë të fshehur mund ti
çasemi duke i parapri me operatorin me emrin e klasës i ndjekur nga operatori i fushëveprimit të
rezolucionit (::). Ndryshoreve globale të fshehura mund ti çasemi me operatorin unar të
fushëveprimit të rezolucionit (shih)
Operatori pikë i selektimit të anëtarit (.) kombinohet me një emër të objektit ose me një
referencë në një objekt për çasje në anëtarët e objektit. Operatori shigjetë i selektimit të anëtarit (→)
kombinohet me tregues në një objekt për çasje në anëtarët e objektit. (Shembulli12).
Bazat e gjuhës programuese C++ S. Bekteshi 105

Shtesa.1

Lokacionet e memorjes

Memorja e kompjuterit mund të paramendohet si një varg i kubëzave. Çdo kubëz – lokacion
i memorjes – është një nga shumë e shumë kubëza të vargisur dhe që janë të numruar në mënyrë
sekuenciale (njëri pas tjetrit). Këta numra njihen si adresa të memorjes. Çdo kubëz është i madh një
bajt. Një ndryshore rezervon një ose më shumë kubëza (pra një ose më shumë bajt) ku mund të
ruhet vlera.
Emri i ndryshores është një emërtim i njërit prej këtyre
kubëzave që dhërben për gjetjen e tij pa e dijtur fare adresën e tij
(Fig. 13).
Figura.13
1. // Prg.18 Programi për mbledhjen e dy numrave të plotë
2. #include <iostream.h>
3.
4. int main()
5. {
6. int int1, int2, shuma; // deklarimi
7. cout << "Shtype numrin e pare \n"; // kërkon
8. cin >> int1; // lexon një integer
9. cout << "Shtype numrin e dyte\n"; // kërkon
10. cin >> int2; // lexon një integer
11. shuma = int1 + int2; // shuma
12. cout << "Shuma eshte " << shuma << endl; //shtyp shumën
13.
14. return 0; // tregon se programi ka përfunduar me sukses
15. }
Dalja: Shtype numrin e pare 2
Shtype numrin e dyte 2
Shuma eshte 4

Analizë: Të shqyrtojmë pjesën e programit prg.18


a) int1 45
cin >> int1;
cin >> int2; b) int2 72
shuma = int1 + int2;
Çdo ndryshore ka emrin tipin, vlerën dhe madhësinë. Emrat e c) shuma 117
ndryshoreve si int1, int2 dhe shuma në të vërtetë iu përgjigjen
lokacioneve të memorjes së kompjuterit (Figura2) Kur të ekzekutohet Fig.14
urdhëresa:
cin>>int1;
vlera e shtypur nga shfrytëzuesi, vendoset në lokacionin e memorjes në të cilin emri int1 i është
shënuar nga kompajlleri i C++.nëse shfrytëzuesi e shtyp numrin 45 si vlerë për int1 kompjuteri do
ta vendos 45 në lokacionin int1 siç është paraqitur në fig.14a). Kur vlera vendoset në lokacionin e
memorjes, ajo e zëvendson vlerën e mëparshme që ka qenë në atë lokacion. Vlera e mëparshme
shkatrrohet.
Kthehemi në programin tonë kur të ekzekutohet urdhëresa:
cin>>int2;
Bazat e gjuhës programuese C++ S. Bekteshi 106

she nëse shfrytëzuesi e shtyp numrin 72 si vlerë për int2. kjo vlerë vendoset në lokacionin e
memorjes int2 dhe memorja duket si në fig.14b. Kur programi i ka fituar vlerat për int1 dhe
int2 ai i mbledh këto vlera dhe i vendos në ndryshoren shuma. Urdhëresa:
shuma=int1+int2;
që kryen mbledhjen gjithashtu e shkatrron vlerën. Kjo ndodh kur shuma e llogaritur e int1 dhe
int2 vendoset në lokacionin shuma (pa marrë parasysh se çfarë vlere ka pasë shuma ajo vlerë
shkatrrohet). Pasi që është llogaritur shuma, memorja duket si në fig.14c). Të theksojmë se vlerat e
int1 dhe int2 janë plotësisht të njejta me ato para se të përdoreshin për llogaritjen e shumës.
Këto vlera janë përdorë por nuk janë shkatërruar kur kompjuteri i ka krye llogaritjen. Kështu, kur
vlera lexohet nga lokacioni i memorjes, ky proces është joshkatërrues
Bazat e gjuhës programuese C++ S. Bekteshi 107

Shtesa.2
Qarqet logjike

Shumë probleme të elektronikës bashkohore zgjidhen me ndihmën e rrjetave ndërprerëse të


cilat shpesh janë mjaft të komplikuara. Pasi në këto rrjeta shfrytëzohen kryesisht qarqet ndërprerëe
me dy gjendje atëherë për përpunimin e këtyre rrjetave është përpunuar një algjebër speciale –
algjebra ndërprerëse, ndryshoret e së cilës mund t’i kenë vetëm dy vlera. Kjo algjebër quhet edhe
algjebra e Bulit sipas emrit të autorit të saj (George Boole) i cili shumë më herët e ka zbuluar në
logjikën e të menduarit. Për këtë arsye vlerat e ndryshoreve të saj quhen logjike ndërsa qarqet në të
cilat ato vlera mund të paraqiten edhe fizikisht - qarqe logjike.

Operacionet logjike

Për shprehjen e ndryshoreve të pavarura në algjebrën e Bool-it shfrytëzohen kryesisht


shkronjat e mëdha të alfabetit. Pasi këto ndryshore mund t’i kenë vetëm dy vlera shifrore 0 dhe 1.
në algjebrën e Bool-it është e zakonshme të thuhet “vlera logjike zero L(1) “ dhe ”vlera logjike një
L(1)”.
Rregullat e algjebrës së Bulit dallohen mjaft shumë nga rregullat e njohura të algjebrës
klasike. Para se gjithash duhet theksuar se funksionet e Bulit definohen me ndihmën e tri
operacioneve themelore: mbledhjes, shumëzimit dhe komplementimit. Operacionet e mbledhjes dhe
shumëzimit shënohen në të njejtën mënyrë si edhe në algjebrën klasike kurse operacioni i
komplementimit nuk ka ndonjë simbol të veqant kështu që vlera komplementare shënohet me një

vizë mbi simbolin e ndryshores. Kështu p.sh. për A=1 dhe B=0 kemi që A  B që shprehet si “A

është e barabartë me komplementin e B”. Gjithashtu edhe nëse A=1 mund të shkruhet A  0 .
Edhepse operacionet e Bulit të mbledhjes dhe të A
shumëzimit, n’a përkujtojnë operacionet përkatëse në
algjebrën klasike, interpretimi i ketyre operacioneve është
plotësisht tjetër. Kjo rrjedh nga ajo se ndryshores së Bulit P
mund ti jipet vetëm një vlerë nga dy të mundshmet,
respektivisht që vlera e ndryshores duhet të shqyrtohet si
një gjendje e caktuar e objektit të vrojtuar. Kështu p.sh.
mbledhja logjike A+B nuk interpretohet si “A plus B” por B
si “A ose B”. Shihet pra, se shenja “ + ” në mbledhjen
logjike shprehet si “ose”, dhe për këtë arsye mbledhja Ilustrimi i operacionit logjik OSE
logjike shënohet si operacioni OSE. Kuptimi thelbsor i
kësaj mbledhje është paraqit në fig. Është e qartë se
llamba elektrike në qark do të ndizet nëse është i mbyllur ose ndërprerësi A ose ndërprerësi B ose të
dy ndërprerësat (A dhe B). Pra nëse për gjendjen e llambës së ndezur marrim vlerën e Bulit 1
atëhere kuptimi i shumës A+B është i ilustruar mjaft qartë
Interpretimi i shumëzimi logjik gjithashtu dallon nga shumëzimi në algjebrën klasike. Kështu
p.sh. shumëzimi logjik A*B nuk shprehet si “A herë B” por si A B P
“A edhe B”. Shihet pra se këtu shenja “ * ” shprehet si “ edhe
”dhe për këtë arsye shumëzimi logjik quhet operacioni EDHE.
Kuptimi i këtij operacioni është ilustruar në fig. Është e qartë se
llamba elektrike në qark do të ndizet vetëm kur është i mbyllur Ilustrimi i operacionit logjik
ndërprerësi A edhe ndërprerësi B. Për këtë arsye gjendja e tillë EDHE
Bazat e gjuhës programuese C++ S. Bekteshi 108

në qark shprehet me shumëzim A*B = 1.


Operacioni i komplementimit paraqet në të vërtetë negacionin e vlerës ose gjendjen e shprehur
me ndryshoren e dhënë. Për këtë arsye komplementimi thirret edhe si operacioni JO. Kështu p.sh. për
funksionin logjik A * B thuhet “A dhe komplement B” ose “A dhe jo B”.

Operacionet elementare

Operacioni OSE

Më parë theksuam se operacioni i mbledhjes i Bulit kryhet me ndihmën e qarkut logjik OSE ka
shumë hyrje A,B,C…N e vetëm në dalje Y. Logjika e qarkut të tillë A
qëndron në atë që ekzistenca e daljes Y është e kushtëzuar me B Y=A+B
ekzistencën e cilësdo hyrje A ose B ose C ose…N ose shumë hyrje së Qarku OSE
bashku. Thënë në mënyrë më precize kjo dmth se në daljen e qarkut OSE
vendoset gjendja e njëshit logjik në rastin kur në njërin apo më shumë A B Y
hyrje veprojnë sinjalet, vlerat e të cilave iu përgjigjen gjithashtu njëshit
logjik. Operacioni i tillë OSE nganjëherë quhet edhe disnjuksion (ndarje) 0 0 0
që shënohet me “ v ” (nga latinishtja ”vel” që dmth ”njëri ose tjetëri ose të 1 0 1
dy bashkë”). 0 1 1
Në fig. Është paraqit grafikisht qarku OSE me dy hyrje me të cilat 1 1 1
sillen sinjalet të paraqitur me A dhe B. Sipas logjikës së dhënë për
operacionin OSE, funksioni i Bulit për këtë qark e ka formën: Tabela funksionale
Mbledhja logjike
Y=A+B (“A ose B”)
Nëse në funksionin e dhënë zëvendësohen të gjitha vlerat e mundshme të ndryshoreve A dhe
B dhe për to përcaktohet vlera përkatëse për Y fitohet tabela e kombinimeve për qarkun OSE e
paraqitur më lartë në figurë.

Operacioni EDHE

Operacioni i shumëzimit i Bulit kryhet me ndihmën e qarkut EDHE. Në fig është paraqitur
simboli grafik i tij me dy hyrje. Logjika e qarkut të tillë qëndron në atë
që dalja Y ekziston vetëm nëse ekzistojnë të gjitha daljet A dhe B dhe C A Y=A· B
dhe ,,,N njëkohësisht. B
Operacioni EDHE respektivisht shumëzimi logjik ose Qarku EDHE
konjuksioni (lidhje) siç quhet edhe ndryshe – shënohet me simbolin ” * ”
ose ” ^ ” i cili shprehet si “edhe” prandaj logjika e paraqitur e qarkut A B Y
paraqitet me funksionin:
0 0 0
Y=A^B=A·B (“A edhe B”) 1 0 0
0 1 0
Me zëvendësimin e të gjithave vlerave të mundshme të
1 1 1
ndryshoreve A dhe B në këtë funksion fitohet tabela e kombinimeve për
qarkun EDHE (Fig.).
Tabela funksionale
Shumëzimi logjik
Bazat e gjuhës programuese C++ S. Bekteshi 109

Operacioni JO

Operacioni i komplementimit i Bulit kryhet me ndihmën e qarkut logjik JO. Në fig. është
paraqiur simboli grafik i qarkut të tillë. Për dallim nga qarqet e
mëparshme, ky ka vetëm një hyrje dhe natyrisht, vetëm një dalje. A ◦ Y=A
Logjika e qarkut JO qëndron në atë që sinjali në hyrje nuk mund
Qarku JO
të ketë vlerë të njejtë si sinjali në dalje. Me fjalë tjera kjo dmth se
në dalje të qarkut vendoset gjendja e njëshit logjik kur në hyrje

është sinjali me vlerë logjike zero dhe anasjelltas. Për këtë arsye Qarku JO paraqitet me rrethin
operacioni i komplementimit quhet edhe negacion kurse qarku në përbërje të qarqeve tjera
JO – negator ose inventor. Prandaj funksioni i qarkut JO në fig.
është dhënë me shprehjen: A Y
Y A 0 1
dhe shprehet si “komplement A ose ”jo A”. Tabela e 1 0
kombinimeve të
Tabela funksionale
qarkut JO është mjaft e thjeshtë dhe është dhënë në fig. Komplementimi logjik

Operacioni logjik JOOSE

Qarqet elementare logjike OSE, EDHE dhe JO zbatohen për kryerjen e operacioneve logjike
të mbledhjes, të shumëzimit dhe të komplementimit dhe për këte arsye, siç kemi treguar edhe me
parë, këto operacione quhen edhe OSE, EDHE dhe JO. Qarqet e dhëna janë plotësisht të
mjaftueshme për interpretimin fizik të çfardo funksioni në algjebrën ndërperëse dhe për këtë arsye
këto qarqe i takojnë të njejtës bazë. Më bazë nënkuptohet tërësia e qarqeve logjike me të cilët mund
të realizohen të gjitha funksionet ndëreprerëse. A Y=A· B
Gjatë projektimit të rrjetave ndërprerëse zakonisht vihet edhe B
kushti që ato duhet të ndërtohen duke shfrytëzuar bazën e cila përmban Qarku JOOSE
një numër sa ma të vogël të qarqeve logjike themelore. Kështu psh
ekziston edhe baza të cilën e formon vetëm një qark logjik siç është A B Y
JOEDHE dhe JOOSE kurse rrjetat nërprerëse të realizuara duke
0 0 1
shfrytëzuar bazën e tillë quhen homogjene. Qarqet e theksuara 1 0 0
JOEDHE dhe JOOSE realizohen me ndihmën e qarqeve elementare 0 1 0
logjike. Me lidhjen e invertorit në daljen e qarkut elementar OSE 1 1 0
fitohet qarku JOEDHE fig. Ky qark përmban operacionet logjike JO-
OSE kështu që funksioni i Bulit për këtë qark shprehet me Tabela funksionale
komplementin e funksionit e qarkut elementar OSE . Operacioni logjik JOOSE

Y  A B
Ky funksion tregon se në rastin e ekzistencës së sinjalit në cilëndo hyrje gjendja e fituar
në dalje nuk do t’i përgjigjet njëshit logjik por zeros logjike. Tabela e kombinimeve e qarkut fig.
paraqet edhe atë se njëshi logjik në dalje kushtëzon praninë koncidente të zerove logjike në të
gjitha daljet. Duhet të theksojmë se ky fakt është plotësisht i kundërt me atë i cili është konstatuar
në qarkun elementar EDHE.
Bazat e gjuhës programuese C++ S. Bekteshi 110

Operacioni logjik JOEDHE

Duke ia shtuar në dalje të qarkut elementar EDHE fitohet A ◦ Y=A· B


qarku JOEDHE fig. Logjika e këtij qarku bazohet në operacionet B
JO-EDHE. Për këtë arsye ajo shprehet me komplementimin e Qarku JOEDHE
funksionit të qarkut elementar EDHE: A B Y
Y  AB
0 0 1
Tabela e kombinimeve,fig, tregon se ky qark ka vlerën e 1 0 1
njëshit në të gjitha rastet përveç kur sinjalet ngacmuese veprojnë 0 1 1
njëkohësisht në të gjitha hyrjet. 1 1 0

Tabela funksionale
Operacioni logjik EX-OSE Operacioni logjik JOEDHE

Logjika e qarkut elementar OSE, siç kemi theksuar më parë, e siguron gjendjen e njëshit
logjik në dalje, kur ekziston sinjali në cilëndo hyrje ose në shumë hyrje njëkohësisht. Mirëpo
logjika e qarkut ekskluziv EX-OSE kushtëzon formimin e gjendjes A
logjike të njëshit në dalje gjatë ekzistencës së sinjalit ngacmues. B ◦ Y=A· B
Logjika e tillë e qarkut në hyrjet A dhe B, fig, mund të shprehet me
Qarku EX-OSE
funksionin: (ose ekskluzive)
Y  AB  AB  A  B A B Y

Simboli “  ”shënon operacionin logjik “ekskluzive OSE” 0 0 0


kështu që funksioni i mësipërm shprehet si”ekskluzivisht A dhe B”. 1 0 1
Nga relacioni shihet se ky funksion i përmban të gjitha operacionet 0 1 1
logjike elementare: EDHE, OSE dhe JO. Duhet të theksojmë se me 1 1 0
zbatimin e disa qëndrimeve tjera të algjebrës ndërprerëse ky relacion
mund të merr forma të tjera. Kjo dmth se logjika e qarkut EX-OSE të Tabela funksionale
Operacioni EX-OSE
kryhet edhe me kombinimet tjera të qarqeve elementare logjike

Operacioni logjik EX-JOOSE

Gjendja e njëshit logjik në dalje të qarkut elementar EDHE sigurohet me veprim koincident
të sinjaleve ngacmuese në të gjitha hyrjet. Mirëpo operacioni logjik A
◦ Y=A· B
“inkluziv edhe” kushtëzon formimin e gjendjes së njëshit logjik në B
dalje jo vetëm në ekzistencën koincidente por edhe gjatë Qarku EX-JOOSE
mosekzekutimit koincident të sinjalit në të gjitha hyrjet e qarkut. Me (inkluzive EDHE)
fjalë tjera, dalja te ky qark ekziston nëse ekzistojnë njëkohësisht të A B Y
gjitha ose nëse njëkohësisht nuk ekziston asnjë hyrje.
Qarku inkluziv EDHE i njohur edhe si qarku koincident 0 0 1
është paraqitur në fig. Funksioni logjik i këtij qarku tregon pra se të 1 0 0
dy hyrjet janë të barabarta dhe shkruhet në formën: 0 1 0
_ _ 1 1 1
Y  A B  AB  A  B Tabela funksionale
Simboli”  ” paraqet operacionin “inkluziv edhe” kështu që funksioni Operacioni EX-JOOSE
i dhënë shprehet si ”inkluzive A dhe B” edhe ky funksion përmban (inkluzive EDHE)
Bazat e gjuhës programuese C++ S. Bekteshi 111

të gjitha operacionet logjike elementare. Të theksojmë edhe këtu se logjika e qarkut inkluzive
EDHE mund të realizohet edhe me kombinime tjera të qarqeve elementare logjike.
Duke i krahasuar tabelat funksionale respektivisht kombinatorike të qarqeve inkluzive
EDHE dhe inkluzive EDHE në fig. shihet se funksionet logjike të këtyre qarqeve janë
komplementare. Pëe arsye operacioni “inkluziv EDHE” zakonisht kryhet me qarkun logjik EX-OSE
me negacionin shtesë. Prej këtu rrjedh se edhe shprehja logjike e dhënë për këtë funksion me
relacionin 0 mund të shkruhet në formë:
Y  A B  AB  A  B

You might also like