-
3
-
1.
I
-
OJI PASKAITA:
Pradin
ės sąvokos
1.1.
C programavimo kalbos ypatybės
•
Gerai išvy
styta aukšto lygio programavimo kalba
.
•
Dauguma (vos ne visos
)
komercinės programos parašytos būtent C arba C
++ kalba.
De facto tai pramoninių
programų rašymo standartas
•
Kada atsirado C kalba? 1969 metais i
š
leista
C kalbos pirma versija. Sukurta kaip sudėti
nė UNIX operacinės sistemos
dalis. Vėlesnės UNIX versijos parašytos C kalba
•
Kodėl pavadinta C? Buvo dvi ankstesnės versijos
–
A ir B, bet jos buvo nevykusios. Iš trečio karto pasisekė sukurti
pasisekusią programavimo kalbą. Todėl ir pavadinimas C.
•
C
–
tai
nepriklausoma nuo mašinos tipo procedūrinė programavimo kalba
•
Koks skirtumas tarp C ir C++? C++
–
tai objektinis procedūrinės programavimo kalbos C poaibis
•
Kokias programas galima parašy
ti naudojant C/C++
?
1
.2. Programavimo kalbų klasifikacija
•
Kas yra k
alba ? Ar pvz. matematika kalba ?
•
Kokios kalbos yra natūralios ir kokios dirbtinės ?
•
Kodėl programos nerašomos natūralia kalba ? Kas nulėmė tokią programavimo kalbų struktūrą kokia yra dabar ?
•
Ţemo lygio programavimo kalbos:
•
-
mašininiai kodai
•
-
asemb
leriai (ypatybės ?)
•
Aukšto lygio programavimo kalbos:
•
-
procedūrinės: Fortran, Pascal, C
•
-
interpretatoriai: Basic
•
objektinės: C++, Java, Delphi (ypatybės ?)
1.3.
Programavimo priemonių rinkinys
•
Ką reikia turėti norint parašyti veikiančią programą ?
Tr
ys pagrindiniai komponentai:
Redaktorius
–
tam, kad parašyti programos išeities kodą. Tinka bet koks
redaktorius (pvz. Notepad
), bet daţniausiai
naudojami specializuoti
Kompiliatorius
–
tam, kad parašytą programos kodą paversti į mašininius kodus, taip vad
inamą objektinį modulį
Linkeris
–
kad prie objektinio modulio prijungti kitus objektinius modulius, bibliotekose surinktą kodą ir gauti
vykdomąją programą.
•
Šiuolaikinėse sistemose daţniausiai naudojamos integruotos sistemos, apjungiančios visus tris komp
onentus
•
Vis daţniau naudojamas vizualinis programavimas. Tačiau sunkiausią dalį programuotojas vis tiek turi padaryti pats
1.4.
C kalbos programavimo priemonės
Yra sukurta daug programavimo priemonių rašyti programas C kalba:
Nemokamos: gcc kompiliatoriu
s, Mars C, lcc ir t.t.
Komercinės: Microsoft C, Borland C, Symantec C ir t.t.
Įprastinės: Turbo C, Borland C, Symantec C
Vizualinio programavimo: Microsoft Visual C, Borland C Builder
•
Kurios geriausios ? Tos, prie kurių labiausiai esi pripratęs ir gali
greičiausiai pasiekti reikiamą tikslą.
1.5. Programos leksika ir sintaksė
•
Programą, parašytą C kalba, sudaro vienas arba keli failai
•
Kiekvieną failą sudaro funkcijų ir kintamųjų bei veiksmų su jais aprašymas
•
Leksiškai programa susideda iš bazinių arba
raktinių ţodţių (angl. keywords) specialių ţenklų, identifikatorių,
konstantų ir komentarų
•
C kalboje naudojamos tiek didţiosios, tiek maţosios raidės, tačiau yra priimta eilė neoficialių susitarimų, kurių
pravartu laikytis
-
4
-
1.6. Kintamieji ir konstantos
•
D
uomenys, kuriuos apdoroja kompiuteris
–
tai konstantos ir kintamieji
•
C kalboje visi kintamieji turi būti
aiškiai
aprašyti
•
Kintamojo aprašymas
–
tai jo tipo specifikavimas, kintamojo vardo uţdavimas, eilė neprivalomų modifikatorių, kurie
apibrėţia vidines
kintamojo vaizdavimo ypatybes arba jo saugojimo klasę.
•
Aprašant kintamąjį galima nurodyti jo pradinę reikšmę
•
Identifikatorius
–
tai seka raidţių arba skaičių, kurie prasideda raide arba pabraukimo ţenklu _
•
Kintamojo
vardas
–
tai
identifikatorius
. Vardas
gali būti bet kokio ilgio, bet tik pirmi 32 simboliai bus reikšminiai
1.7.
Kintamųjų tipai
•
Tipas
–
bet kuriai programavimo kalbai fundamentali sąvoka
•
C kalboje skiriami 4 kategorijų tipai
•
Tuščias
tipas (
void
)
•
Skaliarinis
tipas:
–
aritmetiniai tipai
–
išvard
ijimai (
enumerations
)
–
rodikliai (
pointers
)
–
nuorodos (
references
)
•
Tipas
funkcija
•
Agreguotas
tipas:
–
masyvai (
arrays
)
–
struktūros ir sąjungos
–
klasės (tik C++ poaibyje)
•
Kitaip kintamieji gali būti skirstomi į :
–
pagrindinius
–
išvestinius
•
Pagrindiniai
tipai C ka
lboje yra:
void char int float double
ir jų variantai su raktiniais žodžiais
short long signed unsigned
•
Išvestiniai
tipai:
–
rodikliai ir nuorodos į kitus duomenų tipus
–
funkcijos
–
struktūros ir sąjungos
–
klasės
1.8.
Duomenų tipas
int
•
C kalboje duomenų tipas int (
integer, integral
?) savyje apjungia duomenų tipus
char, short, long
•
Pats duomenų tipas int yra bazinis ir priklauso nuo operacinės sistemos skiltiškumo: jo dydis lygus operacinės
sistemos adresavimo skiltiškumui (16 bitų
Win16, 32 bitai Win32, ateityje 64 bitai ?)
•
bitai
min
max
C
har
8
-
128
127
unsigned char
8
0
255
short int
16
-
32768
32767
I
nt
16
-
32768
32767
unsigned int
16
0
65535
L
ong
32
-
2147413648
2147483647
unsigned long
32
0
4294967295
-
5
-
1.9.
Sveiko tipo
konstantos
•
Sveiko tipo (int) konstantos gali būti uţrašomos dešimtaine, aštuntaine arba šešioliktaine sistema
:
•
15,5,65,156,253
•
015,05,065,0156,0253
•
0x15,0x5,0x65,0x156,0x25af
•
Dešimtainės konstantos paprastoje formoje suprantamos kaip short int kintamieji.
•
Jeigu reikia uţrašyti didesnius kintamuosius, reikia naudoti tipo modifikatorius
U(u)
–
unsigned
arba
L(l)
–
long
•
Pvz.: negalima rašyti
40156 , 1256789,
-
35674
ir t.t.
•
Reikia rašyti
40156u, 1256789l,
-
35674l
ir t.t.
•
Galima naudoti tiek
U
ir
L
, tiek
u
ir
l
1.10.
Slankaus kablelio konstantos
•
Sveikais tipais negalima aprašyti trupmeninių skaičių: reikia naudoti slankaus kablelio tipus
•
C kalboje naudojami trys slankaus kablelio duomenų tipai
:
float, double, long double
bitai
min
max
t
ikslumas
float
32
3,4
*
10
-
38
3.4*1038
7
double
64
1.7*10
-
308
1.7*10308
15
long double
80
3.4*10
-
4932
3.4*104932
19
1.11.
K
intamųjų aprašymo pavyzdžiai
Keli kintamųjų aprašymo pavyzdžiai:
•
int i;
•
signed short a; unsigned short k;
•
short a, b
=
125
, abcd=0xabcd;
•
unsigned cha
r b1=156;
•
float bb, c=0.0,z=1.e
-
5;
•
double pi=3.1415928;
•
long double c1; double _z1erw=123.4561;
1.12.
Pri
ė
jimo modifikatoriai
const
ir
volatile
•
Neprivalomi modifikatoriai padeda apibrėţti kintamuosius, kurie programos vykdymo metu gali arba negali pake
isti
savo reikšmes
•
const
–
negali
•
volatile
–
gali (naudojamas pagal nutylėjimą)
•
•
Pvz:
const int max_const
=
32767
;
•
Naudojama, kuomet norima apsidrausti, kad programos vykdymo metu netyčia nebūtų pakeista reikalinga kintamojo
reikšmė
1.13.
Komentarai
•
C/ C++
kalboje komentarus galima įterpti dviem būdais:
1) /* ..... */
-
komentarai rašomi tarp slešo ir ţvaigţdės ir ţvaigţdės ir slešo. Komentarų kiekis neribojamas
2)
// po dviejų slešų visa eilutė iki galo traktuojama kaip komentarai
Pvz.
/* aš čia dabar rašau
komentarus
kiek noriu tiek rašau. ir čia komentaras int a/c;
dabar baigiu */
int a; // o dabar komentarai , int a
–
čia irgi komentaras
-
6
-
1.14.
Gero stiliaus reikalavimai
Naudoti prasmingus pavadinimus globaliniams kintamiesiems ir trumpus pavadinimus
–
lokaliniams
Patartina globalinių kintamųjų aprašymus paydėti trumpu komentaru
•
Pvz:
int npending
=0; // ivedimo srauto einamas ilgis
•
Pvz:
numberOfPoints
–
globalinis kintamasis
•
nPoints
–
tiek globalinis, tiek lokalinis
•
n
–
lokalinis kintamasis
Egzistuoja dau
g susitarim
ų ir vietinių tradicijų kaip reikėtų parinkti pavadinimus kintamiesiems įvairiose sistemose ir
uţdaviniuose
Būkite nuoseklūs: panašios kilmės objektams reikėtų parinkti atitinkamus pavadinimus, parodančius jų
panašumus ir skirtumus
Būkite tikslū
s: vardas reiškia ne tik objektą, bet ir jo prasmę
!!!
1.15.
Operacijos ir i
š
rai
š
kos
Išraiška
–
tai seka operandų, operacijų ir skiriamųjų ţenklų.
Skiriamieji simboliai: [ ] { } , ; : ... *
= #
Išraiškas kompiliatorius interpretuoja grieţtai besilaikydam
as vyresniškumo taisyklių
Vyresniškumo taisyklės kaip matematikoje priimtos
1.16.
Pagrindinės operacijos: aritmetinės operacijos
Tipinės operacijos
:
•
Sumavimo operacija +
•
Atėmimo operacija
–
•
Daugybos operacija *
•
Dalybos operacija /
C kalbos specifinės o
peracijos:
•
Liekanos nustatymo operacija
%
•
Inkremento operacija ++
•
Dekremento operacija
--
1.17. Pagrindin
ė
s operacijos:
poskiltinės loginės operacijos
•
Vadinamos poskiltinėmis todėl, kad loginiai veiksmai atliekami su kiekviena kintamojo arba konstantos s
kiltimi atskirai
•
Yra keturios:
•
&
-
loginis IR (AND operacija)
•
^
-
poskiltinis sumavimas moduliu 2 (XOR operacija)
•
|
-
loginis ARBA (OR operacija)
•
~
poskiltinė inversija
1 operandas
2 operandas
AND
OR
XOR
0
0
0
0
0
1
0
0
1
1
0
1
0
1
1
1
1
1
1
0
1.1
8.
Pagrindinės operacijos: postūmio operacijos
•
Poskiltinio postūmio
operacijos:
>>
-
postūmis dešinėn
<<
-
postūmis kairėn
Pvz: half
= addr>>1;
double = addr<<1;
Pvz: 5
-
> 101 <<1
-
> 1010
-
> 10
12
-
> 1100>>1
-
> 110
-
> 6
3
-
> 11
<<3
-
> 11000
-
> 24
Priskyrimo operacija
=
. Pvz.
a=b;
-
7
-
1.19.
Pagrin
dinės operacijos: loginės operacijos ir santykio operacijos
Santykio operacijos:
•
>
-
daugiau
•
<
-
maţiau
•
==
-
tapačiai lygu
•
>=
-
daugiau arba lygu
•
<=
-
maţiau arba lygu
•
!=
-
nelygu
•
Teising
a, jei operandas iš kairės tenkina sąlygą
Loginės operacijos
:
•
&&
-
loginis IR
•
||
-
loginis ARBA
•
!
–
loginis NE
•
Šios
operacijos naudojamos sudarant logines išraiškas, turinčias tik
dvi reikšmes: 1, jei išraiška teisinga ir 0, jei
išraiška neteisinga
1.20
.
Sąlygos operacija
? :
•
Sąlygos operacija ? : apibrėţiama kaip:
cond ? TRUE_statement : FALSE_statement
•
Pvz:
int a
=4, b=3;
int i;
i=a>b ? a: b;
1.21.
Duomen
ų tipų nurodymo operacija (kastingavimas)
•
C kalboje duomenų tipus (operandų tipus) galima nu
rodyti aiškiai
•
Toje operacijoje kintamasis bus traktuojamas kaip nurodyta privedimo operacijoje
•
C++ operuojant su skirtingo tipo operandais duomenų tipus būtina kastinguoti
•
Kintamasis
įgis nurodytą tipą tik duotoje operacijoje;
pvz.:
int a=8,b=5;
float va
r1,var2;
var1=a/b; // var1=1.0;
var2=(float)a/b; // var2=1.6;
var2=(float)a/(float)b; // var2=1.6;
1.22.
M
i
nimali programa C kalba
•
int main() { }
•
int main()
{
}
•
int main(
)
{}
Pastabos: failo pavadinimas baigiasi
plėtiniu .c arba .cpp
Tarpus kompili
atorius ignoruoja
Orientuotas į leksemas, o ne pozicijas faile
1.23.
Pirmos programos pavyzdys
#include <stdio.h>
int main() {
unsigned int count;
count=1;
printf(―Hello world !!!
\
n count=%d‖,count ); }
Rezultatas:
Hello world !!! count=1
-
8
-
2.
II
-
OJI PA
SKAITA
2.1.
Bazinio
įvedimo/ išvedimo metodai
•
Skirtingi metodai naudojami konsoliniame įvedime/išvedime ir programose su langais
•
Čia kalbame apie konsolinį I/O
•
C++ turi savus operatorius, C specialių operatorių neturi
•
Naudojamos bibliotekinės funkcijos
•
K
as yra biblioteka, kas yra funkcija ?
•
Standartinė įvedimo / išvedimo biblioteka:
•
#include <stdio.h>
•
Konsolinio
įvedimo / išvedimo biblioteka
•
# include <conio.h>
2.2. Formatuotas i
švedimas
•
Pavadinimas
:
p
rintf()
•
Sinopsė
:
•
#include <stdio.h>
•
int printf(
const format[,arg]...)
•
Apra
šymas: į standartinį išvedimo įrenginį (koks įrenginys yra standartinis ?) išveda nurodytą duomenų srautą,
sutinkamai su nurodytu formatu format: tai gali būti literaliniai simboliai ir transformavimo specifikatoriai:
•
%d
–
dešimtai
nis sveikas skaičius
•
%f
-
slankaus kablelio skaičius
•
%o
-
aštuntainis skaičius be ţenklo
•
%x
-
šešioliktainis skaičius be ţenklo
2.3.
Formatuotas i
švedimas
•
Pavadinimas
:
p
rintf()
•
Sinopsė
:
•
#include <stdio.h>
•
int printf(const format[,arg]...)
•
Apra
šyma
s: į standartinį išvedimo įrenginį (koks įrenginys yra standartinis ?) išveda nurodytą duomenų srautą,
sutinkamai su nurodytu formatu format: tai gali būti literaliniai simboliai ir transformavimo specifikatoriai:
•
%d
–
dešimtainis sveikas skaičius
•
%f
-
sl
ankaus kablelio skaičius
•
%o
-
aštuntainis skaičius be ţenklo
•
%x
-
šešioliktainis skaičius be ţenklo
Pavyzdţiai:
•
printf(―iveskite varda:‖);
•
printf(―turim
a
s akciju skaiciu
s
%d
\
n‖,num);
•
printf(―
\
n sio menesio %2d diena nupirkta %3d akciju
\
n‖,diena, num);
•
p
rintf(―vieneto kaina %f‖, kaina);
•
printf(―vieneto kaina %4.2f bendra kaina %6.2f
\
n‖,kaina, total);
•
printf(―vienetu skaicius %d vieneto kaina %4.2d bendra kaina %6.2f
\
n‖,kiekis, kaina, total);
•
printf(― | vienetu skaicius %d vieneto kaina %4.2d bendra kaina
%6.2f |
\
n‖,kiekis, kaina, total);
2.4.
Konsolinis
įvedimas
•
Pavadinimas
:
scanf()
•
Sinopsė
:
•
#include <stdio.h>
•
int
scanf
(const format[,arg]...)
•
Apra
šymas: iš standartinio įvedimo įrenginio (koks įrenginys yra standartinis ?) nuskaito nurodytą duomenų
srautą, sutinkamai su nurodytu formatu format:
•
%d
–
dešimtainis sveikas skaičius
•
%f
-
slankaus kablelio skaičius
•
%o
-
aštuntainis skaičius be ţenklo
-
9
-
•
%x
-
šešioliktainis skaičius be ţenklo
•
%c
-
simbolis
•
scanf(―
%
d‖
, &num
);
•
scanf
(―
%f‖,&price);
•
scanf(―%d %d‖,&diena, &num);
•
scanf(―%4.2f %6.2f‖,&kaina, &tot
al);
•
scanf(―%d %f %f‖,&kiekis, &kaina, &total);
•
scanf(―%c‖,&raide);
•
scanf(―%d‖,a[i]);
•
scanf(―%s‖ pavadin);
2.5.
Simbolinis
įvedimas/ išvedimas
•
Pavadinimas: getchar
–
įvedimo funkcija
•
Sinopsė:
•
#
include <stdio.h>
•
int getchar(void)
Aprašymas:
nuskaito ir
graţina eilinį simbolį iš standartinio nuskaitymo įrenginio
Diagnostika:
graţina EOF simbolį, jeigu pasiektas failo galas arba klaidos simbolį, įvykus įvedimo klaidai. Visais kitais
atvejais graţina nuskaitytą simbolį
•
Pavadinimas: putchar
–
išvedimo fu
nkcija
•
Sinopsė:
•
#
include <stdio.h>
•
int putchar(int c)
Aprašymas:
išveda eilinį simbolį į standartinį išvedimo įrenginį
Diagnostika:
graţina išvestą simbolį, jeigu išvedimas atliktas sėkmingai, priešingu atveju graţina EOF simbolį.
•
Pavyzdţiai
#include <s
tdio.h>
int main() {
int c;
c=getchar(); /* nuskaito simboli ir priskiria ji kintamajam c */
putchar(c);
putchar( ̳m‘);
putchar( ̳
\
t‘);
putchar( ̳
\
007‘);
}
2.6.
Skaičiavimo proceso valdymo operatoriai
•
Skaičiavimo procesas
–
tai programos operatorių vykdy
mo seka
•
Paprastai programos operatoriai vykdomi elės tvarka: iš viršaus į apačią, iš kairės į dešinę
•
Kartais normalią veiksmų vykdymo seką reikia pakeisti
•
Kam reikia pakeisti valdymo seką ? Uţdavinio sprendimas reikalauja
•
Naudojami specialūs operatoriai
–
skaičiavimo proceso valdymo operatoriai
•
Šakojimosi operatoriai, sąlygos operatoriai, ciklo operatoriai
•
if, if
-
else, while, do while, switch
–
case
-
break, for, break, continue, goto, return
2.7. Operatorius
if
•
Šakojimosi operatoriai išrenka programoje
galimą proceso tąsą iš eilės alternatyvų
•
C kalboje yra du šakojimosi operatoriai
–
if
ir
switch
•
if
–
paprasčiausias sąlygos operatorius
•
if
operatoriaus apibrėţimas:
if(cond_expression) TRUE_statement;
•
cond_expession
–
sąlygos išraiška
•
TRUE_statement
–
i
šraiška, kuri vykdoma jei sąlyga teisinga
-
10
-
•
Pavyzdţiai:
•
if(x>largest) largest
=
x;
•
if( val<min || val>max) {
printf(“reiksme %d iseina uz leidziamo diapazono ribu
\
n”,val);
printf(“leidziamas diapazonas %d %d
\
n”, min, max); }
•
if(num<0) num=
-
num;
•
c=getchar()
;
if(c==„
\
n‟) lines+=1;
•
ekvivalentinis
if((c=getchar()) ==„
\
n‟) lines+=1;
•
neekvivaletinis
if(c=getchar()==„
\
n‟) lines+=1;
2.8. Operatorius if
-
else
if ir else
–
ra
ktiniai žodžiai
•
Jeigu išraiška teisinga
–
vykdoma pirmoji išraiška, jeigu išraiška neteising
a
–
pirmoji išraiška praleidţiama ir
vykdoma antroji išraiška
•
Tiek pirmoji, tiek antroji išraiškos gali būti paprastos arba blokinės
•
Apibrėţimas:
•
if(cond_expression) True_statement;
else False_statement;
•
cond_expession
–
sąlygos išraiška
•
TRUE_statement
–
išraiška, kuri vykdoma jei sąlyga teisinga
•
FALSE_statement
–
išraiška, kuri vykdoma, jei sąlyga neteisinga
Pavyzdžiai
•
if(kiekis<100) printf(―atsargu kiekis mazas‖);
else printf(―atsargu kiekis pakankamas‖);
•
if(x
!=0)
y=y/x;
else {
printf(―klaida: dalyba
is nulio‖);
y=0; }
•
if(hour>=3 && hour<17)
rate*=1.02;
else if(hour>=17 && hour<23)
rate*=1.01;
else rate*=0.99;
Pastaba
:
operatoriai if
-
else yra inkliuzyviniai: į vieną if
-
else operatorių galima įstatyti kitą.
Inkliuzyvų kiekis neribojamas
2.9.
Else
atskyrimo problemos: klaidų šaltinis
•
i
f(c>‘ ̳)
if(c>= ̳0‘ && c<= ̳9‘)
digits+=1;
else
count+=1;
•
Kuriam if priskiriamas else ?
•
i
f(c>‘ ̳)
{
if(c>= ̳0‘ && c<= ̳9‘)
digits+=1;
}
else
count+=1;
-
11
-
2.10.
Operatoriai switch
-
case
-
break
•
Daţnai pasitaikantis programavimo uţdavinys: išrinkti vieną alternatyvą iš daugelio galimų variantų
•
Tai patogu atlikti naudojant switch
-
case operatorių
•
Operatoriaus sintaksė:
switch(switch_expression) {
cas
e const1: statement1; [break;]
case const2: statement2; [break;]
....
case constn: statementn; [break;]
[default: statemnt n+1;]
}
•
Iliustracija
•
input
=getchar();
switch
(input) {
case „d‟: z=z*5;
case „a‟:
case „A‟: z
-
=1; break;
case „p‟:
case „P‟: z+=1; break;
default: printf(“neteisingas pasirinkimas
\
n”);
break;
}
2.11.
Ciklo operatoriai
•
Ciklas
–
tai tų pačių veiksmų pakartojimas nurodytą skaičių kartų
•
C kalba turi tris ciklo uţrašymo formas:
•
while(cond_expression) operators;
•
do operators while(cond_expression);
•
for(init_expr; cond_expr; incr_expr) operators;
•
Kur
i uţrašymo forma geriausia ? Priklauso nuo konkrečių sąlygų
•
Visomis uţrašymo formomis galima uţrašyti bet kurį ciklą
2.12.
Besąlyginio perėjimo operatoriai
•
Yra keturi besąlyginio perėjimo operatoriai C kalboje:
break, continue, goto, return
•
Besąlyginio p
erėjimo operatoriai
–
sutikus tokį operatorių programos valdymas automatiškai perduodamas į apibrėţtą
vietą
•
break
–
išeina iš duoto bloko ir tęsia vykdymą iš karto nuo sekančio operatoriaus uţ bloko
•
continue
–
naudojamas cikle, automatiškai pereina prie s
ekančios ciklo iteracijos
•
return
–
grįţta iš funkcijos. valdymas perduodamas į funkcijos iškvietimo tašką
•
goto label
–
valdymas automatiškai perduodamas į programos tašką, kurį ţymi markeris label
2.13.
Gero stiliaus reikalavimai
1) Formatuokite kodą tai
p, kad pabrėžti jo struktūrą
•
Blogas formatavimas:
for(n
++;n<100;n++) field[n++]=„
\
0‟;
*i=„
\
0‟; return(„
\
n‟);
•
Geras formatavimas:
for(n++;n<100;n++)
field[n++]=„
\
0‟;
*i=„
\
0‟;
return „
\
n‟;
2)
rašykite išraiškas
natūralia forma: rašykite taip, kaip skaitytumėte
Blogai:
if(
!(block_id<actblk) || !(block_id>=unblock))
-
12
-
Gerai:
if(
(block_id>=actblk) || (block_id<unblock))
3)
Naudokite skliaustelius, kad panaikinti neaIŠKUMUS
•
Pavyzdys su kelintiniais metais
•
leap_year
= y%4==0 && y%100!=0 ||y%400==0;
•
leap_year= ((y%4==0) && (y%100!=0)) ||(y%400==0);
4) Skaidykite sudėtingas išraiškas:
•
Blogai:
x+=(xp=(2*k<(n
-
m) ? c[k+1] : d[k
--
]));
•
Gerai
:
if(2*k<n
-
m)
xp=c[k+1];
else
xp=d[k
--
];
x+=xp;
5)
B
ūkite paprastesni: nereikia persistengti rašant labai įmantrias išraiškas:
•
Blogai:
subkey=subkey>>(bitoff>>3)<<3));
•
Gerai:
subkey=subkey>>(bitoff&0x7));
subkey>>=bitoff&0x7;
Absoliučiai mįslin
ga konstrukcija:
child=(!LC&&!RC)?0:!(LC?RC:LC);
Paprastai:
if(LC==0 && RC==0)
child=0;
else if(LC==0)
child=RC;
else
child=LC;
6) Būkite atsarg
ūs u pašaliniais efektais: ++ tipo operacijos turi pašalinius efektus: jos ne tik gražina reikšmę, bet ir
pakeičia operando reikšmę
•
Blogai:
str[i++]=str[i++]=„A‟;
(
blogai, nes nėra apibrėţta ++ operacijos vykdymo tvarka)
•
Gerai:
str[i++]
=„A‟;
•
str[i++]=„A‟;
3.
III
-
IOJI PASKAITA:
Rodyklės
. Nuorodos. Masyvai
.
3.1.
Rodyklės
sąvoka
•
Idėja panaudoti adresus
–
labai sena.
•
Programose rašomose mašininiais kodais arba asembleriu daţnai sutinkamas uţdavinys
–
perkelti duomenis iš vieno
adreso į kitą
•
Tok
iose programose tai atliekama paprastai
•
Aukšto lygio programavimo kalbose daţnai apie adresus negalvojama, o kai kuriose ir nėra jokių priemonių operuoti su
adresais
•
C kalboje yra abiejų būdų komponentų: tiek darbui su adresais, tiek ir ne tiesioginio adr
esavimo galimybių
•
Kas yra rodiklis? Kintamasis, kuriame saugomas adresas
•
Apibrėţimas: kntamasis
-
rodiklis (arba tiesiog vadinama rodikliu)
–
ta kintamasis, skirtas adreso saugojimui atmintyje
•
Kam naudojami rodikliai?
Kad efektyviai prieiti prie duomenų
La
nksčios programos parašymui
Kintamųjų, perduodamų į funkciją, reikšmių pakeitimui
Darbui su dinamiškai paskirstoma atmintimi
Priėjimui prie aparatinių kompiuterio resursų arba papildomų įrenginių
3.2.
Rodyklės
ir nuorodos
C kalboje
•
C kalboje apibrėţtos d
vi specialios operacijos kintamųjų adresavimui per rodiklius
o
operacija
&
-
nuorodos (reference)
operacija
o
operacija
*
-
rodiklio (pointer) operacija
Operacijos
&
rezultatas
–
tai objekto, kuriam taikoma i operacija, adresas
Operacija
*
–
tai kreipinys į a
tminties ląstelę, kurios adresas saugomas tame objekte
-
13
-
3.3.
Rodiyklės
aprašymas, inicializavimas ir naudojimas
•
Kintamasis p aprašomas kaip rodiklis į sveiko tipo kintamąjį. Tai reiškia kad jame bus saugomas sveiko tipo kintamojo
adresas
•
int num1
=3, num2=6
, *p;
•
Visi rodikliai turi būti inicializuoti
•
p=&num1;
•
Rodiklis p
dabar ―rodys‖ į kintamąjį num1
•
Dabar kintamąjį num1 bus galima adresuoti tiesiogiai, naudojant priskyrimo operaciją
=
, arba kaip rodiklį, naudojant operatorių
*
3.4.
Dar
a
pie rodykles
•
Svarbu prisiminti, kad ţenklas *
-
tai operatorius
•
Kuomet jis naudojamas su dviem operandais (binarinis operatorius)
–
tai daugybos operatorius
•
Kuomet jis naudojamas kaip unarinis operatorius
–
laikoma, kad tai rodiklis, nurodantis į ţenklą
•
N
egalima sumaišyti
•
Sudėtingose išraiškose kartais gali būti painu suprasti kaip reikia perskaityti
•
Pvz: p
= a* *b *c **d;
3.5.
Pratimai su rodyklėmis
: operacijos
&
ir *
•
Kas neteisinga ţemiau pateiktoje programoje
#iclude <stdio.h>
int main()
}{
int num1=100, *p;
printf(“num1 is %d
\
n”,num1);
printf(“*p is %d
\
n”,*p);
}
Ar tokia programa bus sukompiliuota?
Ar bus įvykdyta ?
Kas bus išspausdinta ?
#include <stdio.h>
main() }{
int num1=3, num2=6;
int *p;
p=&num1;
printf(―%d
\
n‖,*p);
*p=20;
printf(―%d‖,*p);
printf(―%d
\
n‖,num1);
p=&num2;
printf(―%d
\
n‖,*p);
}
•
510 p ?
•
504 num2 6
•
500 num1 3
•
510 p 500
•
504 num2 6
•
500 num1 3
•
510 p 500
•
504 num2 6
•
500 num1 20
•
510 p 504
•
504 num2 6
•
500 num1 20
•
Kas bus išvesta atlikus šitą programą
#include <stdio.h>
int main(){
int count=10,
x;
int *ip;
ip=&count;
x=*ip;
printf(―count=%d, x=%d
\
n‖,count,x); }
•
Kas bus išvesta atlikus šitą programą
#include <stdio.h>
int main(){
int i1,i2;
int *p,*q;
i1=5;
p=&i1;
i2=*q/2+10;
q=p;
printf(―i1=%d i2=%d‖,i1,i2);
printf(―*p=%d *q=%n‖,*p,*q); }
-
14
-
3.6.
Rody
klių aritmetika
•
Svarbu aprašant rodiklius su teisingu duomenų tipu
•
Naudojama padidinan
t / sumaţinant rodiklio reikšmę, palyginant rodiklius tarpusavyje, atimant vieną rodiklį iš kito ir
pan
•
char
*p;
•
*p
–
tai simbolis
•
p++ ekvivalent
iška p
=p+1
•
short *p;
•
*p
–
tai trumpas sveikas skai
čius
•
p++
-
ekvivalentiška p
=
p+2
3.7.
Masyvai
•
Masyvas
–
ta
i eilės tvarka, vienas paskui kitą, atmintyje išdėstyti vieno ir to paties tipo elementai.
•
Kiekvienas masyvas turi nuosavą unikalų pavadinimą
•
Priėjimas prie masyvo elementų atliekamas naudojant masyvo pavadinimą ir elemento eilės numerį
•
Pagrindinis masyv
o privalumas: leidţia saugoti aibę elementų, aiškiai nenurodant kiekvieno iš elementų pavadinimų
•
Masyvai gali būti vienmačiai arba daugiamačiai (dvimačiai, trimačiai, ir t.t. Kada pabaiga ?)
•
Masyvo poţymis
–
kvadratinių skliaustelių buvimas šalia pavadinim
o:
char buffer[256]; int a[3];
ir t.t.
•
Pagrindinės masyvų savybės C kalboje:
1)
Visi masyvo elementai yra vieno ir to paties tipo
2)
Aprašant masyvą nurodomas jo elementų tipas, masyvo pavadinimas ir bendras masyvo elementų skaičius
3)
Pirmo masyvo elemento indek
sas visada yra lygus 0, paskutinio n
-
1
4)
Masyvo elementai į atmintį surašomi nuosekliai (pvz. 3 elementas atmintyje visada bus po 2)
5)
Dvimačiai masyvai surašomi eilutėmis: pirmiausia pirmos eilutės elementai, po to antros ir t.t.
•
Masyvo vardas yra rodiklis
-
k
onstantė (tiesiog rodiklis) ir visada lygus masyvo pradžios adresui
3.8.
Masyvo inicializavimo būdai
•
C kalboje numatyti du masyvų inicializavimo būdai:
•
Inicializavimas pagal nutylėjimą: taikomas tik statiniams arba išoriniams masyvams
•
Tiesioginė element
ų inicializacija:
•
char array[10]
={„a‟,‟b‟,‟c‟,‟d‟,‟e‟,‟f‟,‟g‟,‟h‟,‟i‟,‟j‟};
•
char array[]={1,2,3,4,5};
•
char array[5]; array[0]=1; array[1]=2; array[2]=3;
•
char array[10]; int i; for(i=0;i<10;i++) array[i]=i;
3.9.
Nuorodos į masyvo elementus
•
Darbas su at
skirais masyvo elementais arba indekso, arba operacijos * pagalba
•
Abu darbo su masyvo elementais būdai yra lygiaverčiai
•
Naudojant indeksus
•
masyvo_vardas[sveikaskaitinė_išraiška]
•
Short a[15]; a[0]
=5; a[2]=7; a[5]=a[0]+a[2]; a[7]=a[5];
•
Naudojant rod
iklius:
•
s
hort a[15];
*
a
=5; *(a+2)=7; *(a+5)=*a+*(a+2); *(a+7)=*(a+5);
3.10.
Daugiamačiai masyvai
•
C kalba palaiko ir daugiamačius masyvus
•
Masyvo matiškumas
–
tai indeksų, naudojamų adresuojant masyvo elementą, skaičius
•
Daugiamačių masyvų elementai
saugomi atmintyje dešiniausio indekso didėjimo tvarka
•
Dvimačio masyvo vardas yra rodiklis į rodiklių masyvą. Masyvo elementai yra rodikliai į kiekvienos eilutės pradţios
elemento adresą
•
Matiškumų skaičius nėra ribojamas, praktiškai niekada nenaudojami dide
sni nei trimačiai masyvai
-
15
-
3.11.
Programos su masyvais pavyzdys
#include <stdio.h>
int main() {
const float investment=6000, interest=.085;
float rate; double value[5];
int year;
rate=1+interest; value[0]=investment; year=1;
while(year<5) {
value[year]=value[year
-
1]*rate;
year+=1; }
printf(―pradinis indelis %.2f
\
n‖,value[0]);
year=1;
while(year<5) {
printf(―metai %d: %.2f
\
n‖,year,value[year]);
year+=1; } }
3.12.
Kelios pastabos apie masyvus
•
C kalboje nėra atliekamas joks masyvų adresavimo korektiškumas
•
Tai daţna klaidų prieţastis: adresuoti į tuos masyvų elementus, kurių pagal pradinį masyvo aprašymą paprasčiausiai
nėra
•
Viena iš daugiamačių masyvų reto naudojimo prieţasčių
–
didesnis adresavi
mo sudėtingumas ir didesnė klaidų
tikimybė
short a[30]; for(i
=0
;i<30;i++)
a[i]=i*i; //gerai
a[30]=a[29]; // blogai , tik 30 elementu galima
a[7*7]=a[5*5] // blogai
Visa
atsakomybė uţ indeksų naudojimo teisingumą išimtinai priklauso progr
amos autoriui
Jei adresuojama į masyvo elementą su didesniu indeksu, programa nulūţta
3.13.
Masyvų kopijavimas
•
Masyvai turi būti kopijuojami elementas po elemento
•
Int prev[20],current[20];
•
Neteisingai:
prev
=
current;
//
kompiliavimo kla
ida
•
Teisingai:
i=0;
while(i<20) {
prev[i]=current[i];
i+=1; }
3.14.
Inkremento ir dekremento operatoriai
masyvuose
•
Dėl savo patogumo ir efektyvumo inkremento/ dekremento operatoriai daţnai na
udojami veiksmuose su masyvais
•
Prefiksinė forma ++x,
--
x; postfiksinė forma x++,x
—
•
Prefiksinė forma
–
reikšmė pakeičiama nedelsiant, postfiksinė
–
reikšmė pakeičiama atlikus kitus veiksmus
•
x
=3; y=++x; // y? x?
•
x
=3; y=x++; // y? x?
•
Pvz:
i=0;
i=0;
while(<size) { => while(i<size) table[i++]=0;
table[i]=0;
i=i+1;
}
3.15.
Simbolių masyvai
•
Labai daţnai pasitaikantis uţdavinys: apdoroti tekstą (tekstinę informaciją)
•
Tekstas k
ompiuterio poţiūriu
–
tai simbolių rinkinys. Bet mums reikia ne atskirų simbolių, o jų junginių
-
16
-
•
Kiekvienas teksto simbolis kaip ir masyvo elementas, nes visi elementai vienodo tipo
•
Bet tokie masyvai specifiniai
–
tarpai, taškai, ir t.t. Kur pabaiga masyvo
?
•
Daţnai iš anksto neţinomas teksto ilgis, daţnai būna kintamas
•
Kitose kalbose (naujesnėse) simbolių sekų saugojimui yra skirti specialūs duomenų tipai, C to neturi
•
Tokie duomenų tipai vadinami simbolių eilutėmis arba stringais
•
Uţrašymas: simbolių eilutė
–
tai seka bet kokių simbolių, įtrauktų į dvigubas porines kabutes
•
Simbolių eilutė C kalboje kompiuterio atmintyje saugoma kaip char tipo elementų masyvas, kurio pabaigoje yra
simbolis ̳
\
0‘ (null
-
terminatorius)
•
Stringas
–
tai simbolių seka, pasibaigianti
simboliu nul
-
terminatoriumi. Todėl jo ilgis visada vienetu didesnis negu
yra prasmingų simbolių
!!!!!
•
Da
ţnai pamirštama, kad stringui reikia išskirti vienetu daugiau, negu numatome saugoti simbolių. Aišku galima
rezervuoti ir dar daugiau atminties ląsteli
ų.
3.16.
Stringų aprašymai
•
Aprašoma kaip ir char tipo duomenų masyvas:
•
Ekvivalentiški aprašymai:
•
char string[]
=
”eilute”;
•
char string[7]=“eilute”;
•
char string[7]={„e‟,‟i‟,‟l‟,‟u‟,‟t‟,‟e‟,‟
\
0‟};
•
char *string=“eilute”;
Pastaba
:
svarbu suprasti
, kad priski
riant eilutės reikšmę į rodiklio string atminties ląstelę persiunčiama ne visa eilutė, o tik
jos pirmojo elemento adresas. Todėl stringų, kaip ir kitų masyvų, negalima perkopijuoti prilyginant jų pavadinimus
3.17.
Eilučių
apdorojimas
•
Veiksmams su simboli
ų eilutėmis yra parašyta daug standartinių funkcijų
•
Reikia įtraukti header failą string.h, kad galėtume operuoti tomis funkcijomis
•
#include <string.h>
•
Keli pavyzd
ţiai:
•
strcpy(src,dest)
–
perkopijuoti vieną eilutę į kitą
•
strcmp(src,dest)
–
palyginti vieną
eilutę su kita
•
strcat(str1,str2)
–
prijungti vieną eilutę prie kitos
•
Ir dar daug kitų funkcijų
Pavyzdys su
stringais
#include <stdio.h>
int main() {
int i;
char first[11];
printf(“prasau ivesti varda:”);
i=0;
whi
le(i<10 && (first[i]=getchar()) !=„
\
n‟)
i+=1;
first[i]=„
\
0‟;
printf(“ivestas vardas: %s
\
n”,first);
}
3.18.
Masyvai kaip rodyklės
•
Masyvų aprašymas su kvadratiniais skliausteliais paprastas ir patogus būdas tačiau
turi trūkumų:
•
Negalima rezervuoti didelių masyvų
(didesni
ų
negu 32676 elementai)
•
Masyvo dydį reikia nurodyti iš karto ir negalima vėliau jo keisti (daţnai nelengva iškarto nustatyti kokio dydţio masyvo mums
reikės)
•
Yra antras masyvų aprašymo būdas, neturi
ntis tokių apribojimų
–
masyvų aprašymas per rodiklius:
•
Pvz: short
*a; long *b;
Ta
č
iau
kol kas nenurody
tas masyvo dydis. Tą būtina padaryti
!!!
-
17
-
3.19.
Masyv
ų dydžio nurodymas
•
Naudojamos standartinės funkcijos, aprašytos header faile alloc.h:
•
#include <a
lloc.h>
•
Atminties rezervavimui naudojamos funkcijos
malloc()
ir
farmalloc(),
atminties atlaisvinimui naudojamos funkcijos
free()
ir
farfree().
•
Atmintį atlaisvinti būtina, kai ji nėra reikalinga
•
Reikalingos atminties dydis šiose funkcijose visada uţduodamas
baitais . Todėl reikia pačiam apskaičiuoti reikalingą
baitų skaičių arba pasinaudoti komanda
sizeof()
Masyvų dydţio nurodymo pavyzdys
•
Reikia 100 elementų trumpų skaičių masyvo ir 300 elementų slankaus kablelio skaičių masyvo
•
Pvz:
#include <alloc.h>
int
main() {
short *a;
float *b;
a=malloc(200); // nes kiekvienas short tipo elementas 2 baitai
a=malloc(100*sizeof(short)); // arba taip
b=farmalloc(
1200); // nes kiekvienas float elementas 4 baitai
b
=farmalloc(300*sizeof(float)
) // arba taip
......
free(a); farfree(b); }
3.20.
Dinaminiai masyvai
•
Aprašant masyvus kaip rodiklius galima pakeisti masyvui išskirtos atminties kiekį programos vykdymo metu
•
Tam daţniausiai naudojamos funkcijos realloc() arba farrealloc();
•
Dydis ir vėl nurodomas baitais
•
Pvz:
short
*a;
a=malloc(10);
a=realloc(a,20);
•
Pastaba: nepriklausomai nuo masyvo aprašymo būdo, masyvo elementus galima adresuoti abiem anksčiau nurodytais
būdais
4. IV
-
OJI PASKAITA: Funkcijos.
4.1.
Bendros sąvokos apie funkcijas
•
Kas yra funkcija ?
•
Vieną funkcijos sąvoką ţ
inote iš matematikos. Ką reiškia funkcija matematikoje ?
•
Programavime funkcija turi panašumų, bet turi ir daug esminių skirtumų
•
Sąvoka paprogramė (
subroutine
) naudota daugelyje ankstyvųjų programavimo kalbų (pvz. Fortran, PL/1, Cobol ir
t.t.)
•
Paprogramė
–
tai programos dalis , gebanti atlikti analogiškus veiksmus su skirtingais kintamaisiais
•
Funkcija kiek platesnė sąvoka nei paprogramė
4.2.
Funkcijos apibrėžimas
•
Egzistuoja keletas funkcijos apibrėţimų
•
Funkcija
–
tai operatorių grupė, atliekančių išbaigtą
veiksmų seką. Į funkciją galimą kreiptis pagal pavadinimą,
perduoti jai argumentus ir gauti iš jos reikšmę
•
Funkcija
–
tai logikai savarankiška programos dalis, turinti savo pavadinimą, kuriai gali būti perduodami parametrai
ir kuri gali graţinti reikšmę
•
Pi
rmas apbrėţimas techniškesnis, antras
–
labiau atspindintis reikalo turinį
4.3.
Funkcijos
•
C kalba parašyta programa
–
tai iš esmės funkcijų rinkinys. Funkcijos išdėstytos bet kuria tvarka. Faktiškai funkcijos
gali būti išdėstytos keliuose failuose.
•
C k
albos koncepcijoje numatyti visi paprogramių tipai: funkcijos ir procedūros
-
18
-
•
Funkcijos leidţia rašyti programą moduliniu būdu: kiekviena funkcija atlieką tam tikrą uţdavinį. Tokias programas
ţymiai lengviau skaityti
•
Funkcijos leidţia išvengti analogiškų vei
ksmų dubliavimo
•
Daugelis programų gali naudoti tas pačias funkcijas, todėl nereikia perrašinėti kiekvieną kartą.
4.4.
Funkcijos aprašymas
Funkcijos aprašymo standartas atrodo taip:
•
[
duomenu_tipas] funkcijos_vardas(argumentu_sarasas) {
kintamuju apra
symai;
....... // funkcijos_kunas
operatoriai;
[return (israiska)];
}
[]
–
skliausteliuose pateikti neprivalomi funkcijos elementai
4.5.
Funkcijos aprašymo paaiškinimas
•
Laukas ―duomenų tip
as‖ nurodo funkcijos graţinamos reikšmės tipą jeigu jis nėra nurodytas, pagal nutylėjimą
laikoma, kad funkcija graţina
int
tipo reikšmę. Jeigu lauke ―duomenų tipas‖ nurodytas raktinis ţodis
void
, tuomet
funkcija negraţina jokios reikšmės.
•
Laukas ―funkcijo
s pavadinimas‖
–
tai ypatingas rodiklio tipas, vadinamas rodikliu į funkciją. Jo reikšmė yra lygi
įėjimo
į funkciją pradţios adresui. Funkcijos pavadinimas be
to yra identifikatorius ir sudaromas pagal
identifikatoriams C kalboje keliamus reikalavimus.
•
Lau
kas ―argumentų sąrašas‖ apibrėţia argumentus (kartais vadinami parametrais), perduodamus į funkciją.
Argumentų sąrašas gali būti sudarytas iš bet kokios duomenų tipų jų vardų kombinacijos. Argumentų skaičius
neribojamas. Argumentai tarpusavyje skiriami ka
bleliais. Jeigu argumentai nenaudojami, sąraše rašomas ţodis
void
4.6.
Funkcijos prototipas
•
C kalbos standartas reikalauja, kad dar iki pirmo funkcijos iškvietimo programoje būtų pateiktas funkcijos
apibrėţimas
•
Toks pirminis funkcijos apibrėţimas vadinam
as funkcijos prototipu.
•
Prototipas praneša kompiliatoriui apie graţinamos reikšmės tipą, argumentų kiekį ir tipus.
•
Po prototipo dedamas kabliataškis;
•
Daţnai prototipai talpinami į atskirus failus, turinčius plėtinį .h ir vadinamus header
-
failais
•
Standartin
ių funkcijų prototipai pateikti header failuose, kurie įtraukiami su direktyva include
4.7.
Pirmas funkcijos pavyzdys
•
Uţduotis: apskaičiuoti skritulio plotą, kai sp
i
ndulys r
=5,10,27
•
Galima taip:
void main() {
int r1=5,r2=10,r3=27;
float s1,s2,s3;
s1=3.
14159*r1*r1;
s2=3.14159*r2*r2;
s3=3.14159*r3*r3;
}
Funkcijos nenaudojamos
O
galimą ta patį uţrašyti ir taip
float area(int r);
void main() {
int r1=5,r2=10,r3=27;
float s1,s2,s3;
s1=area(r1);
s2=area(r2);
s3=area(r3);
}
float area(int r) {
return(3.14159*r*r); }
Šiuo atveju laimėjimas atrodo nedidelis,
bet jei reikės atl
ikti tarkim 20 veiksmų
funkcijoje ?
-
19
-
4.8.
Formalūs ir aktualūs argumentai
•
Kuomet aprašome funkcijos kūną, nurodome argumentų, kurie turėtų būti perduoti į funkciją, sąrašą.
•
Šie argumentai vadinami formali
ais, su jais veiksmai programos vykdymo metu nebus atliekami
•
Kuomet iškviečiame funkciją, nurodome į funkciją perduodamų argumentų sąrašą.
•
Šie argumentai (tiksliau
–
jų kopijos) programos vykdymo metu bus perduoti į funkciją ir su jais atliekami veiksmai.
Jie vadinami aktualiais argumentais.
•
Privalo sutapti formalių ir aktualių argumentų tipai.
•
Kompiliatorius pasirūpins, kad atitinkamas aktualus argumentas atsidurtų atitinkamo formalaus argumento vietoje.
4.9.
Funkcijos iškvietimas
•
funkcijos_vardas(argum
entų sąrašas)
•
Vykdymas perduodamas į funkciją
•
Atliekami eilės tvarka funkcijos kūne aprašyti veiksmai
•
Įvykdţius sugrįţtama į sekančią po funkcijos iškvietimo einančią operaciją
void intro(void);
int main() {
......
intro();
.....
}
void intro(void) {
printf(“pr
adedamas programos vykdymas
\
n”);
printf(“programos autorius jonukas
\
n”” }
4.10.
Funkcijos argumentai
•
Naudojami informacijos perdavimui į funkciją
•
Į funkciją perduodamos reikšmės, o ne patys kintamieji
•
Yra lokaliniai funkcijos kintamieji
•
Iškviečiant funkc
iją reikia nurodyti tikslų jų skaičių, tipus, ir eilės tvarką
int main() {
float amount
=
250
, interest=0.075;
print_growth(amount,interest);
printf(main: amount= %.2f
\
n‖,amount);
}
void print_growth(float val,float rate) {
val=1+rate)*val;
}
4.11.
Tip
ų
kastingavimas funkcijose
•
Tipų kastingavimas naudojamas laikinam duomenų tipo pakeitimui
•
Naudojamas aiškiam teisingo funkcijos tipo nurodymui
float func(float x);
void func1(int x);
int man() {
int x;
func((float)x);
funcą(x);
}
4.12.
Duomenų perdavi
mas į funkciją
•
Parametrų perdavimui į funkciją egzistuoja du stiliai:
1) funkcijų iškvietimas su reikšmių perdavimu (call
-
by
-
value);
2) funkcijų iškvietimas su kintamųjų adresų perdavimu (call
-
by
-
reference);
-
20
-
•
Iškvietimas su reikšmių perdavimu
–
tai kint
amųjų reikšmių kopijų perdavimas į funkcijos kūną. Tai niekaip
neleidţia pakeisti kintamųjų reikšmes iškvietimo taške
•
Iškvietimas su adresų perdavimu
–
tai kintamųjų adresų kopijų perdavimas į funkcijos kūną. Tokiu būdu mes galime
keisti reikšmes saugomas
nurodytais adresais
4.13.
Kintamųjų reikšmių perdavimo pavyzdys
void suma(int a,int b,int suma);
void main() {
int a
=5,b=7,sum=5;
printf(―sum=%d
\
n‖,sum);
suma(a,b,sum);
printf(―sum=%d
\
n‖,sum);
}
void suma(int a,int b,int suma) {
suma=a+b;
}
void suma(
int a,int b,int suma);
void main() {
int a
=5,b=7,sum=5;
printf(―sum=%d
\
n‖,sum);
suma(&a,&b,&sum);
printf(―sum=%d
\
n‖,sum);
}
void suma(int *a,int *b,int *suma) {
*suma=*a+*b;
}
4.14.
Keli
pavyzdžiai
•
Kas neteisinga šiame funkcijos aprašyme ?
int compute
(int , int ){
int x;
double y;
..... }
Kas bus išspausdinta įvykdţius sekančią programą ?
void square(int val);
int main() {
int x=5;
square(x);
printf(―x lygu %d
\
n‖,x);
}
void square(int val) {
val=val*val:
printf(―%d
\
n‖,val); }
4.15.
Steko reikšmė
•
Stekas
–
ta atminties sritis, kurią vykdanti programa naudojama laikinam saugojimui;
•
Kuomet iškviečiama funkcija, visi šios funkcijos argumentai patalpinami į steką, po to patalpinamos esamų registrų
reikšmės ir kiti parametrai
•
Toks argumentų, registrų ir
automatinių kintamųjų rinkinys, skirtas vienai funkcijai, vadinamas freimu.
•
Jei iškviesta funkcija viduje iškviečią dar vieną funkciją, tai jai sukuriamas dar vienas freimas ir anksčiau steke buvę
parametrai perstumiami tolyn
•
C kalba parašytoms programoms
reikia daug steko, neretai stekas persipildo ir dėl to gali ―nulūţti‖ programa
4.16.
Operatorius
return
•
Graţina reikšmę į iškviečiančią funkciją return išraiška;
•
Nėra privalomas operatorius
-
21
-
•
Negraţina jokios reikšmės jeigu naudojama išraiška
return;
in
t main(){
int len
=50, width=4, area;
area=area_rect(len,width);
printf(“plotas lygus %d
\
n”,area);
return 0; }
int area_rect(int l, in w) {
return l*w; }
4.17.
Masyvai kaip funkcijos argumentai
•
Į funkcija neperduodama viso masyvo kopija
•
Perduodamas tik p
irmo elemento adresas
•
Per šį adresą funkcija gali prieiti prie masyvo elementų, juos modifikuoti.
void main() {
char current[30], target[0];
...
stringcopy(target,current);
... }
void stringcopy(char str1[], char str2[]) {
int i;
for(
i=0; str2[i]!= ̳
\
0‘;i+
+) str1[i]=str2[i];
str1[i]= ̳
\
0‘;
}
4.18.
Vienmačių masyvų perdavimas į funkciją
•
Duoti du sveikų skaičių masyvai. Rasti kuriame iš jų yra daugiau teigiamų skaičių
•
int n_posit(const int
*
a,
const int n) {
int main() {
int i,n;
int a[50], b[50];
printf(“i
veskite elementu skaiciu:”);
scanf(“%d”,&n);
printf(“iveskite elementus:”);
for(i=0;i<n;i++) scanf(“%d %d”,&a[i],&b[i]);
if(n_posit(a,n)>n_posit(b,n)
printf(“pirame daugiau teigiamu elementu);
else if ..
}
int n_posit(const int *a, const int n) {
int
i, count=0;
for(i=0;i<n;i++) if(a[i]>0) count++;
return count; }
4.19.
Stringų perdavimas į funkcijas
•
Parašyti programą, kuri nustatytų kiek simbolių yra eilutėje
int string_elem(char
*str);
void main() { char strp[256];
int elem;
printf(“iveskite simboliu eilute”);
gets(strp);
elem=string(elem);
printf(“stringe yra %d e
leementu
\
n”,elem);
}
int string_elem(char *str) {
int elem;
for(i=0;str[i]!=„
\
0‟;i++)
elem++;
return(elem);
}
-
22
-
4.20.
Parametr
ų perdavimas į funkciją main
•
Kai kada reikia perduoti parametrus į pagrindinę funkciją
main
•
tai naudoja pvz. archyvavimo prog
ramos, dirbančios iš komandinės eilutės
•
[tipas] main(int argc, char
**argv) {
funkcijos kunas
}
arba
•
[tipas] main(int argc, char
**argv, char **env) {
funkcijos kunas
}
4.21.
Standartinės funkcijos
•
Kiekvienoje C programų kūrimo sistemoje yra daug st
andartinių funkcijų
•
Su visa eile standartinių funkcijų jau teko susitikti: printf, scanf
•
Šios funkcijos yra sudėtos į bibliotekas, jų prototipai
–
į header
-
failus, kuriuos reikia įtraukti naudojant direktyvą
include
•
Standartinės funkcijos sugrupuotos pagal
tematiką į grupes, programuotojui reikėtų pasirūpinti reikalingų funkcijų
paieška
•
Pats programuotojas taip pat gali kurti nuosavas funkcijų bibliotekas
4.22.
Parametrų perdavimas į funkciją main
•
Komandinės eilutės ţodţiai tai transformuotos į ASCII for
matą simbolių sekos, atskirtos tarpais, uţduodamos
programos paleidimo metu
•
Programos aplinka
–
tai seka ASCII simboliais išreikštų sekų, kuri tam prieinama programai, jos paleidimo metu
•
Į funkciją perduodamų parametrų prasmė:
int argc
–
ţodţių skaičius k
omandinėje eilutėje
char
**
argv
–
rodiklis į rodiklių masyvą iš
argc
elementų. nulinis elementas
–
visada programos pavadinimas
char **env
–
rodiklis į kintamo dydţio masyvų rodiklį
Pavyzdys programos su
argumentų perdavimu į funkciją main:
#include <std
io.h>
void main(int argc, char
**argv
) {
printf(“i programa perduota %d argumentu
\
n”,argc);
printf(“ perduoti duomenys irasyti faile %s
\
n”, argv[1]);
printf(“paleista programa vadinasi %s
\
n”, argv[0]);
}
4.23.
Rekursinės funkcijos
•
C kalba leidţia funkci
jai iškviesti pačiai save
.
•
Funkcija, besikreipianti p
ati į save vadinama rekursija
•
Kiekvienu atveju steke išskiriama atminties sritis saugoti kintmųjų kopijas ir kitus parametrus
•
Klasika tapusi faktorialo skaičiavimo funkcija:
f(n) {
if(n) return n
*
f(n
-
1);
else return 1;
}