iš 60
Esamasis rodinys
-
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() {