Upload
others
View
2
Download
0
Embed Size (px)
Citation preview
Alapismeretek
Programozás I.
Hatwágner F. Miklós
Széchenyi István Egyetem, Gy®r
2013. szeptember 29.
Forrásfájltól a programfuttatásig
1 Forrásszöveg megszerkesztése (.c kiterjesztés, ASCIIszövegfájl)
elso.c
/* elso.c */
#include <stdio.h>
void main(void) {
printf("Ez egy C program!\n");
}
KimenetEz egy C program!
_
Hatwágner F. Miklós Alapismeretek
Forrásfájltól a programfuttatásig
2 Fordítás (→ compiler)
elso.c fordító elso.obj
Üzenetek típusai:hibaüzenetek (error)�gyelmeztet® üzenetek (warning)
Megjegyzések:
elso.c, 1. sor:
/* elso.c */
/* nyitja és */ zárjatöbb soron át tarthatnem ágyazhatók egymásba
Hatwágner F. Miklós Alapismeretek
Forrásfájltól a programfuttatásig
El®feldolgozó (preprocessor):
egybeépítve a fordítóval
közvetlenül a fordítás el®tt lép m¶ködésbe
elhagyja a megjegyzéseket
végrehajtja, majd elhagyja a direktívákat
elso.cfordító
elso.objelőfeldolgozó
elso.c, 2. sor#include <stdio.h>
Hatwágner F. Miklós Alapismeretek
Forrásfájltól a programfuttatásig
El®feldolgozó direktíva: egy sorban, melynek els® nem fehérkaraktere a #
Fehér karakter (white space): pl. szóköz, soremelés, lapdobás,tabulátor, de még a megjegyzés is
#include: betölti a paraméter szövegfájlt
stdio.h → fejfájl (header): adattípusok, konstansok de�níciói,függvények jellemz®i
standard input/output
< és > jelek: csak egy bizonyos helyen keresi a fájlt (include�les)
Hatwágner F. Miklós Alapismeretek
Forrásfájltól a programfuttatásig
Függvényde�níció
elso.c, 3. sor
void main(void) {
típus függvénynév(formális-paraméterlista) { függvény-test }
visszatérési érték típusa void (→ nincs [másutt: eljárás])
fv. neve main → indító program
formális-paraméterlista mindig ( és ) között, most nincsenek(void)
függvény-test helye: mindig { és } között
Hatwágner F. Miklós Alapismeretek
Forrásfájltól a programfuttatásig
Függvényhívás
elso.c, 4. sor
printf("Ez egy C program!\n");
függvénynév(aktuális-paraméterlista)
printf megjelenteti paraméterét a szabvány kimeneten
karakterlánc konstans: id®z®jelek között
escape szekvencia (vagy jelsorozat, escape sequence):vezérl®jelek, nem nyomtatható jelek, programnyelvi jelentésselbíró jelek megjelenítésére
; → utasításvég jelzés
Hatwágner F. Miklós Alapismeretek
Forrásfájltól a programfuttatásig
Esc. szekv. Jelentés\a �gyelmeztet® jelzés (bell, cseng®)\b visszalépés (backspace)\f lapdobás (form feed)\n új sor (new line)\r kocsi vissza (carriage return)\t vízszintes tabulátor (horizontal tab, HTAB)\v függ®leges tabulátor (vertical tab, VTAB)\\ fordított törtvonal (backslash)\? kérd®jel\' aposztróf\" idéz®jel\ooo oktális szám\xhh hexadecimális szám\0 zérus ASCII kódú karakter
Hatwágner F. Miklós Alapismeretek
Forrásfájltól a programfuttatásig
3 Kapcsoló-szerkesztés (link)fv.-ek tárgykódja: statikus könyvtárakban (.lib) (run-timelibraries, standard libraries)keretrendszerben beállítható ezek és a kimeneti fájlok elérésiútja
elso.objindító
program (obj)könyvtárak (lib)
elso.exekapcsoló-szerkesztő
4 Futtatás
Hatwágner F. Miklós Alapismeretek
Fahrenheit - Celsius átváltás
Feladat:
Számítsuk ki az összetartozó °F � � értékeket 0 és 300°Fközött, °F értékét rendre 20-asával növelve!
� = 59(°F− 32)
Adatstruktúra:
az értékeket konstansként adjuk meg
Algoritmus:
minden értékpárt egyesével meghatározunk, majd értéküketmegjelentetjük
Hatwágner F. Miklós Alapismeretek
Fahrenheit - Celsius átváltás
pelda1.c
/* PELDA1.C -- Fahrenheit - Celsius átszámítás */#include <stdio.h>void main(void){printf("\nFahrenheit - Celsius átszámítás\n\n");printf("%f Fahrenheit - %f Celsius\n", 0., (5.0/9.0)*(0.-32.0));printf("%f Fahrenheit - %f Celsius\n", 20., (5.0/9.0)*(20.-32.0));printf("%f Fahrenheit - %f Celsius\n", 40., (5.0/9.0)*(40.-32.0));printf("%f Fahrenheit - %f Celsius\n", 60., (5.0/9.0)*(60.-32.0));printf("%f Fahrenheit - %f Celsius\n", 80., (5.0/9.0)*(80.-32.0));printf("%f Fahrenheit - %f Celsius\n", 100., (5.0/9.0)*(100.-32.0));printf("%f Fahrenheit - %f Celsius\n", 120., (5.0/9.0)*(120.-32.0));printf("%f Fahrenheit - %f Celsius\n", 140., (5.0/9.0)*(140.-32.0));printf("%f Fahrenheit - %f Celsius\n", 160., (5.0/9.0)*(160.-32.0));printf("%f Fahrenheit - %f Celsius\n", 180., (5.0/9.0)*(180.-32.0));printf("%f Fahrenheit - %f Celsius\n", 200., (5.0/9.0)*(200.-32.0));printf("%f Fahrenheit - %f Celsius\n", 220., (5.0/9.0)*(220.-32.0));printf("%f Fahrenheit - %f Celsius\n", 240., (5.0/9.0)*(240.-32.0));printf("%f Fahrenheit - %f Celsius\n", 260., (5.0/9.0)*(260.-32.0));printf("%f Fahrenheit - %f Celsius\n", 280., (5.0/9.0)*(280.-32.0));printf("%f Fahrenheit - %f Celsius\n", 300., (5.0/9.0)*(300.-32.0));
}
Hatwágner F. Miklós Alapismeretek
Fahrenheit - Celsius átváltás
pelda1.c, 5. sor
printf("%f Fahrenheit - %f Celsius\n", 0., (5.0/9.0)*(0.-32.0));
printf els®, karakterlánc paraméterétkarakterek ésformátumspeci�kációk
alkotják. Utóbbi% karakterrel indul, és típuskarakterrel zárul.A formátumspeci�kációk és printf további akt. paramétereiösszetartoznak (sorrend, mennyiség).%<szélesség><.pontosság>típuskarakter
Típuskarakter Paraméter típusa Megjelenítésd egész típus decimális egészkéntf lebeg®pontos tizedes tört alakc egy karakter karakterkénts karakterlánc karakterláncként
Hatwágner F. Miklós Alapismeretek
Fahrenheit - Celsius átváltás
pelda1.c, kimenet
Fahrenheit - Celsius átszámítás
0.000000 Fahrenheit - -17.777778 Celsius20.000000 Fahrenheit - -6.666667 Celsius40.000000 Fahrenheit - 4.444444 Celsius60.000000 Fahrenheit - 15.555556 Celsius80.000000 Fahrenheit - 26.666667 Celsius100.000000 Fahrenheit - 37.777778 Celsius120.000000 Fahrenheit - 48.888889 Celsius140.000000 Fahrenheit - 60.000000 Celsius160.000000 Fahrenheit - 71.111111 Celsius180.000000 Fahrenheit - 82.222222 Celsius200.000000 Fahrenheit - 93.333333 Celsius220.000000 Fahrenheit - 104.444444 Celsius240.000000 Fahrenheit - 115.555556 Celsius260.000000 Fahrenheit - 126.666667 Celsius280.000000 Fahrenheit - 137.777778 Celsius300.000000 Fahrenheit - 148.888889 Celsius_
Hatwágner F. Miklós Alapismeretek
Fahrenheit - Celsius átváltás
Problémák:
rengeteg feleslegesen ismétl®d® kódrészlet
sok hibalehet®ség
nehézkes karbantarthatóság, stb. → módosítunk!
Adatszerkezet:
Funkció Azonosító Típus Jellegtartomány alsó határa also egész munkatartomány fels® határa felso egész munkalépésköz lepes egész munkaaktuális Fahrenheit érték fahr valós munka, outputaktuális Celsius érték celsius valós munka, output
Hatwágner F. Miklós Alapismeretek
Fahrenheit - Celsius átváltás
Algoritmus:
változók deklarálása, kezd®értékadások
fejlécsor megjelentetése
ciklusmag ismétlése, amíg fahr <= felsociklusmagban: számolás, értékpár kijelzése, fahr léptetése
pelda2.c
/* PELDA2.C -- Fahrenheit - Celsius átszámítás */#include <stdio.h>void main(void) {int also, felso, lepes;float fahr, celsius;printf("\nFahrenheit - Celsius átszámítás\n\n");printf("Fahrenheit - Celsius\n");printf("--------------------\n");also = 0; felso = 300;lepes = 20; fahr =also;while(fahr<=felso) {celsius = (5.0/9.0)*(fahr-32.0);printf("%10.0f%10.1f\n", fahr, celsius);fahr = fahr+lepes;
}}
Hatwágner F. Miklós Alapismeretek
Fahrenheit - Celsius átváltás
Blokkszerkezet
el®ször deklarációs utasítások, majd végrehajtható utasítások(nem keveredhetnek)
minden változót deklarálni kell
Deklarációs utasítás
típus azonosítólista;
azonosítólista: vessz®vel elválasztott azonosítók
Típusok
int el®jeles, �xpontos bels® ábrázolású egész
float 4 bájtos, lebeg®pontos bels® ábrázolású valós(mantissza el®jelével 3 bájt + karakterisztika el®jelével 1 bájt,ábrázolási határok: ±3, 4 · 10−38 � ±3, 4 · 10+38, 6-7 decimálisjegy pontosság)
Hatwágner F. Miklós Alapismeretek
Fahrenheit - Celsius átváltás
Hozzárendelés
pelda2.c, 12. sor
celsius=(5.0/9.0)*(fahr-32.0);
objektum = kifejezés
módosítható balérték: értéket felvenni képes objektum
jobbérték: meghatározható érték¶ kifejezés
esetleges implicit típusmódosítás
Elöltesztel® ciklus
pelda2.c, 11. sor
while(fahr<=felso) {
while(kifejezés) utasítás
kifejezés aritmetikai: igaz (1) esetén ismétli az utasítást, hamis (0) eseténa ciklust követ® utasításra lép
utasítás több utasításból is állhat → { és }
kifejezés-nek változnia kell → végtelen ciklus
Hatwágner F. Miklós Alapismeretek
Fahrenheit - Celsius átváltás
Explicit típusmódosítás(típus)kifejezés
pelda2.c, kimenet
Fahrenheit - Celsius átszámítás
Fahrenheit - Celsius--------------------
0 -17.820 -6.740 4.460 15.680 26.7100 37.8120 48.9140 60.0160 71.1180 82.2200 93.3... ...300 148.9
_
Hatwágner F. Miklós Alapismeretek
Fahrenheit - Celsius átváltás
Probléma
túl sok változó (nem is változik az értékük!) → módosítunk!
pelda3.c
/* PELDA3.C -- Fahrenheit - Celsius átszámítás */#include <stdio.h>void main(void) {int fahr;printf("\nFahrenheit - Celsius átszámítás\n\n");printf("Fahrenheit - Celsius\n");printf("--------------------\n");for(fahr=0; fahr<=300; fahr=fahr+20)printf("%10d%10.1f\n", fahr, (5.0/9.0)*(fahr-32));
}
Hatwágner F. Miklós Alapismeretek
Fahrenheit - Celsius átváltás
Elöltesztel®, iteratív ciklusutasításfor(<init-kifejezés>; <kifejezés>; <léptet®-kifejezés>)utasítás
1 init-kifejezés végrehajtása, ha megadták2 utasítás végrehajtása, ha kifejezés igaz; lehet összetett3 léptet®-kifejezés végrehajtása, ha megadták, majd ugrás a 2.
pontra
while átalakítható for ciklusra:<init-kifejezés>;while(kifejezés) {utasítás; <léptet®-kifejezés;>}
printf paramétere kifejezés is lehetProbléma: konstansok szétszórva a programban → nehézkes, lassúmódosítások, rengeteg hibalehet®ség → módosítunk!
Hatwágner F. Miklós Alapismeretek
Fahrenheit - Celsius átváltás
Szimbolikus állandók (egyszer¶ makrók)
egyszer kell de�niálni, majd a megfelel® helyeken használni ®ket
könny¶ a változásokat átvezetni
#de�ne azonosító helyettesít®-szöveg
pelda4.c
/* PELDA4.C -- Fahrenheit - Celsius átszámítás */#define ALSO 0#define FELSO 300#define LEPES 20#include <stdio.h>void main(void) {int fahr;printf("\nFahrenheit - Celsius átszámítás\n\n");printf("Fahrenheit - Celsius\n");printf("--------------------\n");for(fahr=ALSO; fahr<=FELSO; fahr=fahr+LEPES)printf("%10d%10.1f\n", fahr, (5.0/9.0)*(fahr-32));
}
Hatwágner F. Miklós Alapismeretek
Fahrenheit - Celsius átváltás
Szokás a #define direktívákat külön fejfájlba helyezni, majd arra hivatkozniA fájlnév most idéz®jelek között áll!
beginend.h
/* BEGINEND.H -- saját fejfájl */#define ALSO 0 /* Alsó hatar. */#define FELSO 300 /* Fels® határ. */#define LEPES 20 /* Lépésköz. */#define begin {#define end }#define LACI for#include <stdio.h>
pelda4m.c
/* PELDA4M.C -- Fahrenheit - Celsius átszámítás */#include "beginend.h"int main(void)begin
int fahr;printf("\nFahrenheit - Celsius átszámítás\n\n");printf("Fahrenheit - Celsius\n");printf("--------------------\n");LACI(fahr=ALSO; fahr<=FELSO; fahr=fahr+LEPES)begin
printf("%10d%10.1f\n",fahr,(5.0/9.0)*(fahr-32));end
end
Hatwágner F. Miklós Alapismeretek
Be- és kimenet
Szabványos be- és kimenet
legtöbb operációs rendszer támogatja
stdin (standard input): alapértelmezetten a billenty¶zet
stdout (standard output) alapértelmezetten a képerny®
felhasználó átirányíthatja ezeket (pl. nyomtatóra, fájlba, . . . )
Egy karakter olvasása szabvány bemenetr®l
int getchar(void);
balról nulla érték¶ bitekkel feltölti, int-re alakítva adja vissza
hiba esetén, vagy a fájl végén EOF értéket szolgáltat.
fájl vége billenty¶zeten? Pl. Ctrl+Z
stdio.h részlet
#de�ne EOF (-1)
Függvény prototípusa megadja
a visszatérési érték típusát
a függvény nevét
paramétereinek számát, sorrendjét, típusát
azaz teljes formai információval szolgál a függvényr®l
Hatwágner F. Miklós Alapismeretek
Be- és kimenet
Egy karakter írása a szabvány kimenetre
int putchar(int k);
visszatérési érték sikeres esetben k, hiba esetén ett®l eltér®érték
Készítsünk programot, ami a fájl végéig átmásolja a szabványbemenetr®l érkez® jeleket a kimenetre!
pelda5.c
/* PELDA5.C -- Bemenet átmásolása a kimenetre */#include <stdio.h>void main(void) {int c;printf("\nBemenet másolása a kimenetre:\n\n");printf("Gépeljen Ctrl+Z -ig sorokat!\n\n");c=getchar();while(c!=EOF) {putchar(c);c=getchar();
}}
Hatwágner F. Miklós Alapismeretek
Be- és kimenet
A getchar az OS billenty¶zet pu�eréb®l olvas; ENTER leütéséignem fér hozzá a begépelt karakterekhez!Készítsünk programot, ami megszámolja a szabvány bemenetr®lérkez® jeleket!
pelda6.c
/* PELDA6.C -- Karakterszámlálás */
#include <stdio.h>
void main(void) {
long nc;
nc = 0l;
printf("A bemenet karaktereinek leszámlálása:\n\n");
printf("Gépeljen Ctrl+Z-ig!\n\n");
while(getchar()!=EOF) ++nc;
printf("A bemenet karaktereinek száma %ld volt.\n", nc);
}
Hatwágner F. Miklós Alapismeretek
Be- és kimenet
Adattípus deklaráció, pontosítva
pelda6.c, 4. sor
long nc;
<típusmódosítók> <alaptípus> azonosítólista;
el®jel kezelése: signed (aé.) / unsigned
hosszmódosítók: short / long
még az alaptípus is elhagyható (aé. int), de az alaptípus és atípusmódosítók egyszerre nem hagyhatók el!
short ≤ int ≤ long
pelda6.c, 5. sor
nc = 0l;
az l a long, az u pedig az unsigned utótag
Hatwágner F. Miklós Alapismeretek
Be- és kimenet
Növelés, csökkentés
pelda6.c, 8. sor
while(getchar()!=EOF) ++nc;
növelés, inkrementálás (increment): ++
csökkentés, dekrementálás (decrement): −−unáris → nagyon magas prioritású
el®tag (pre�x) / utótag (post�x) operátor változatok
Az el®tag/utótag operátorok hatása az eredményre
int a, b; b = 6; a = ++b; /* a==7 és b==7 */ a = b++; /* a==7 és b==8 */
pelda6.c, 9. sor
printf("A bemenet karaktereinek száma %ld volt.\n", nc);
Hosszmódosítók: h → short, l → long
Hatwágner F. Miklós Alapismeretek
Be- és kimenet
Feladat: sorok összeszámolása a bemeneten
pelda7.c
/* PELDA7.C -- Sorszámlálás */#include <stdio.h>void main(void) {int c, nl;nl = 0;printf("A bemenet sorainak leszámlálása:\n\n");printf("Gépeljen Ctrl+Z -ig!\n\n");while((c=getchar()) != EOF)if(c == '\n') ++nl;
printf("\nA bemeneten %d sor volt.\n", nl);}
Vö. pelda5.c ↔ pelda7.c megoldását!
c = getchar();while(c != EOF) {if(c == '\n') ++nl;c = getchar();
}
Hatwágner F. Miklós Alapismeretek
Be- és kimenet
Ciklusszervezés összetett kifejezés felhasználásával
�gyelni kell a m¶veletek prioritására!
mi történne zárójelezés nélkül?
Operátor Asszociativitás() [] -> . balról jobbra! ~ ++ −− + - * & (típus) sizeof jobbról balra* / % balról jobbra+ - balról jobbra<< >> balról jobbra< <= > >= balról jobbra== != balról jobbra& balról jobbra^ balról jobbra| balról jobbra&& balról jobbra|| balról jobbra?: jobbról balra= += -= *= /= %= &= ^= |= <<= >>= jobbról balra, balról jobbra
Hatwágner F. Miklós Alapismeretek
Be- és kimenet
Kétirányú szelekció
pelda7.c, 9. sor
if(c == '\n') ++nl;
if(kifejezés) utasítás1 <else utasítás2>
az utasítások lehetnek összetettek, vagy akár
újabb szelekciós utasítások → többágú szelekció
Hatwágner F. Miklós Alapismeretek
Be- és kimenet
Feladat: bemenetr®l érkez® karakterek, szavak és sorokösszeszámolásaAdatszerkezet
vegyünk fel egészeket a karakterek (nc), szavak (nw) és sorok(nl) számlálásához
szükség lesz egy egészre a következ® jel olvasásához (c)
és egy állapotjelz®re (szó belsejében járunk-e, inword)
Algoritmus
számlálókat nullázzuk le, szón kívül állunk
tájékoztató üzenetek megjelenítésekarakterek olvasása ciklussal EOF-ig, közben
nc növelése,nl növelése, ha az utolsó karakter újsor volt,szóhatár észlelése fehér karakterek �gyelésével; szó belsejébelépve nw növelése
végül az eredmények kijelzéseHatwágner F. Miklós Alapismeretek
Be- és kimenet
pelda8.c
/* PELDA8.C -- A bemenet sorainak,szavainak,karaktereinek számlálása */#include <stdio.h>#define YES 1#define NO 0void main(void) {int c, nl, nw, nc, inword;inword = NO;printf("A bemenet karaktereinek,\n");printf(" sorainak és\n");printf(" szavainak leszámlálása:\n");printf("A bemenet vége: Ctrl+Z vagy EOF.\n\n");nl = nc = nw = 0;while((c=getchar()) != EOF) {++nc;if(c == '\n') ++nl;if(c==' ' || c=='\n' || c=='\t') inword=NO;else if(inword == NO) {inword=YES;++nw;
}}printf("sor=%d szo=%d karakter=%d\n", nl, nw, nc); }
Hatwágner F. Miklós Alapismeretek
Be- és kimenet
Többszörös hozzárendelés
pelda8.c, 12. sor
nl = nc = nw = 0;
fontos, hogy nl, nc és nw mind balértékek
asszociativitás
gyorsabb m¶ködés, tömörebb forrásszöveg
Hatwágner F. Miklós Alapismeretek
Tömbök
Feladat: készítsünk programot, mely a szabvány bemenetr®l olvaskaraktereket EOF-ig, s közben megszámolja, hogy az egyesszámjegy karakterekb®l, fehér karakterekb®l és minden máskarakterb®l hány darab érkezett!
Algoritmus
Deklaráljuk az egyszer¶ változókat és a tömböt! A számlálók(beleértve a tömböt is) nullázandók!
Jelenítsünk meg tájékoztató üzenetet!M¶ködtessünk ciklust, amíg EOF nem érkezik a bemenetr®l!Ciklusmagban:
Háromágú szelekcióval ki kell választani a megfelel® kategóriát,majd a neki megfelel® számlálót meg kell növelni!
Megjelenítend®k a számlálók értékei!
Hatwágner F. Miklós Alapismeretek
Tömbök
pelda9.c
/* PELDA9.C -- Számjegyek, üres és egyéb karakterek leszámlálása */#include <stdio.h>void main(void) {int c; /* bemeneti karakter */int i; /* számláló */int nwhite; /* üres karakterek */int nother; /* egyéb karakterek */int ndigit[10]; /* szám karakterek */printf("Számjegyek, üres- és egyeb karakterek leszámlálása\n");printf("a bemeneten EOF-ig vagy Ctrl+Z-ig.\n\n");nwhite = nother = 0;for(i=0; i<10; ++i) ndigit[i] = 0;while((c=getchar()) != EOF)if(c>='0' && c<='9') ++ndigit[c-'0'];else if(c==' ' || c=='\n' || c=='\t') ++nwhite;else ++nother;
printf("Számjegyek\n\n");for(i=0; i<10; ++i) printf("%d = %d\n", i, ndigit[i]);printf("\n\nÜres karakterek = %d\nEgyéb karakterek= %d\n",nwhite, nother);
}
Hatwágner F. Miklós Alapismeretek
Tömbök
Tömb de�níció
pelda9.c, 8. sor
int ndigit[10]; /* szám karakterek */
típus tömbazonosító[méret];
méret pozitív, egész érték¶ állandó kifejezés
állandó kifejezés értéke fordítási id®ben kiszámítható
Tömb helyfoglalása
sizeof(tömbazonosító) ≡ méret*sizeof(típus)
sizeof megadja a típus vagy objektum bájtokban mért méretét
Tömbelemek (indexes változó) elérése
tömbazonosító[index]
0 ≤ index ≤ meret − 1
Hatwágner F. Miklós Alapismeretek
Tömbök
pelda9.c, 12. sor
for(i=0; i<10; ++i) ndigit[i] = 0;
Az i számjegyek számát ndigit[i] tárolja! (Azaz pl. 0-bólndigit[0], 1-b®l ndigit[1], sít. érkezett.)
pelda9.c, 14. sor
if(c>='0' && c<='9') ++ndigit[c-'0'];
A számjegy karakterek kódjai folytonosan követik egymást akódtáblában
c-'0' a két kód különbségét → a megfelel® indexet adja!
Hatwágner F. Miklós Alapismeretek
Függvények
El®re megírtak könyvtárakban (.lib) vagy tárgymodulokban(.obj), pl. printf, getchar,. . .Mi készítjük el!
Feladat: jelezzük ki 2 els® 10 hatványát!
pelda10.c
/* PELDA10.C -- Hatványozó függvény tesztelése */#include <stdio.h>#define MEDDIG 10int power(int x, int n);void main(void) {int i;printf("Kett® hatványai:\n\n");for(i=0; i<MEDDIG; ++i) printf("2**%d = %d\n", i, power(2, i));
}int power(int x, int n) { /* x n-edik hatványa, ha n>0, különben 1 */int i, p;p = 1;for(i=1; i<=n; ++i) p=p*x;return(p);
}
Hatwágner F. Miklós Alapismeretek
Függvények
De�nícióból csak egy létezhet, összhangban a deklarációkkal,prototípusokkal
Prototípus el®zze meg a hívást! Hogyan konvertáljuk aparaméterek típusát?
Paraméterátadás érték szerint
A fv. nem int-et ad vissza? Legalább deklarálni kell!
Függvény deklaráció / prototípus / de�níció elhelyezése
Fv. de�níciók nem ágyazhatók egymásba
Visszatérési érték: return <kifejezés>;
Vt. érték típusa: tömb és függvény nem lehet, aé. int
Implicit típuskonverzió, ha szükséges
return el®fordulásai
Kilépés függvényb®l: return vagy } elérésekor
Hatwágner F. Miklós Alapismeretek
Prodzsekt
Forrásfájlok témánkénti, funkciónkénti csoportosítása
main egy és pontosan egy forrásban szerepelhet!
Prodzsektfájl készítés
fuggv.c
/* FUGGV.C - A power függvény. */int power(int x, int n) { /* x n-edik hatványa, ha n>0, különben 1 */int i, p;p = 1;for(i=1; i<=n; ++i) p=p*x;return(p); }
foprog.c
/* FOPROG.C -- Hatványozó függvény tesztelése */#include <stdio.h>#define MEDDIG 10int power(int x, int n);void main(void) {int i;printf("Kett® hatványai:\n\n");for(i=0; i<MEDDIG; ++i) printf("2**%d = %d\n", i, power(2,i)); }
Hatwágner F. Miklós Alapismeretek
Prodzsekt
foprog.cfordítás
foprog.objfuggv.c fuggv.obj
foprog.objfuggv.obj
indítóprogram (obj)
könyvtárak (lib)
prodzsekt.exekapcsoló-
szerkesztés
Fájlok közötti implicit függ®ség → újrafordítás szükség esetén
Kezelése: automatikusan vagy explicit megadással
stdio.h foprog.c foprog.obj
fuggv.c fuggv.objindító prg.könyvtárak
prodzsekt.exe
Hatwágner F. Miklós Alapismeretek
Karakterláncok
De�níció: char tömbazonosító[méret];
Mérete: méret*sizeof(char) ≡ méret
Indexelés: [0; méret-1]
Karakter konstans bels® ábrázolása: int
Van értelme? nev1 == nev2, nev1<nev2, . . .
nev
0 1 2 3 4
'G' 'i' 'z' 'i' 'k'
5
'e'
6
'\0'
Feladat:
Készítsen programot, amely neveket olvas a szabvány bemenetr®lEOF-ig vagy üres sorig! Megállapítandó és kijelezend® aleghosszabb név!Probléma:
Szöveg beolvasása
Szöveg tárolásaHatwágner F. Miklós Alapismeretek
Karakterláncok
getline()
int getline(char s[], int lim) {
/* Max. lim méret¶ karakterlánc beolvasása s-be.
A függvény a karakterlánc hosszát adja vissza.
s tömbnek lim+1 méret¶nek kell lennie. */
int c, i;
for(i=0; i<lim && (c=getchar())!=EOF && c!='\n'; ++i) s[i]=c;
s[i] = '\0';
return(i);
}
Formális paraméter tömb méret nélküli!Billenty¶zet pu�er problémákat okoz:
karakterek (EOF is!) csak Enter leütés után olvasható kimi történik, ha lim-nél több karaktert gépeltek be?
getline() � pu�er ürítés
while(c!=EOF && c!='\n') c=getchar();
Hatwágner F. Miklós Alapismeretek
Karakterláncok
getline()
int getline(char s[], int lim) {
/* Max. lim méret¶ karakterlánc beolvasása s-be.
A függvény a karakterlánc hosszát adja vissza.
s tömbnek lim+1 méret¶nek kell lennie. */
int c, i;
for(i=0; i<lim && (c=getchar())!=EOF && c!='\n'; ++i) s[i]=c;
s[i] = '\0';
return(i);
}
Formális paraméter tömb méret nélküli!Billenty¶zet pu�er problémákat okoz:
karakterek (EOF is!) csak Enter leütés után olvasható kimi történik, ha lim-nél több karaktert gépeltek be?
getline() � pu�er ürítés
while(c!=EOF && c!='\n') c=getchar();
Hatwágner F. Miklós Alapismeretek
Karakterláncok
copy()
void copy(char s1[], char s2[]) {
/* s1 masolása s2-be. s2-t elég nagynak tételezi fel. */
int i;
i = 0;
while((s2[i]=s1[i]) != '\0') ++i;
}
string.h � strcpy()
stdio.h � getline() POSIX.1-2008
Hatwágner F. Miklós Alapismeretek
Karakterláncok
pelda11.c
/* PELDA11.C -- A leghosszabb szövegsor kiválasztása */#include <stdio.h>#define MAXLINE 1000int getline(char s[],int lim);void copy(char s1[], char s2[]);void main(void) {int len; /* Az aktuális sor hossza */int max; /* Az aktuális max. sor hossza */char line[MAXLINE+1]; /* Az aktuális sor */char save[MAXLINE+1]; /* Az aktuális max. sor */printf("A leghosszabb szövegsor kiválasztása\n");printf("A sorokat zárja le Enter-rel!\n");printf("Utoljára adjon meg egy üres sort vagy Ctrl+Z-t!\n\n");max = 0;while((len=getline(line, MAXLINE)) > 0)if (len>max) {max=len; copy(line, save); }
printf("A leghosszabb sor:\n");if(max > 0) printf("\n%s\n", save); } /* Volt sor */
int getline(char s[],int lim) { ... }void copy(char s1[], char s2[]) { ... }
Hatwágner F. Miklós Alapismeretek
Változók tulajdonságai
Alapfogalmak
Hatáskör/érvényességi tartományAz a programterület, ahol hivatkozható, elérhet®.
ÉlettartamAz az id®szak, amíg memóriát foglal.
Változó de�níciójaOlyan deklaráció, melynek során memóriafoglalás is történik.
Tárolási osztályMeghatározza, hogy az objektum
1 hol jön létre a memóriában (regiszter / statikus /dinamikus terület)
2 de�niálja az objektum élettartamát
Hatwágner F. Miklós Alapismeretek
Változók tulajdonságai
Lokális (bels®) változók
Pl. i a copy(), getline() fv.-ekben
Hatásköre: a blokk, amiben de�niálták (és annak blokkjai;lokális hatáskör)
Élettartama: amíg saját blokkjában van a vezérlés (lokálisélettartam)
Memóriaterület: futásid®ben foglalt, rendszerint a veremben
Alapértelmezett (implicit) kezd®érték: nincs
Alapértelmezett tárolási osztály: auto
Függvények formális paraméterei lokális változók.
Hatwágner F. Miklós Alapismeretek
Változók tulajdonságai
Változó deklarációja, pontosítva
<tárolási-osztály><típusmódosítók><alaptípus>azonosítólista;
Tárolási osztályok:autoregisterstaticextern
Pl. auto i; ≡ auto signed int i;
Hatwágner F. Miklós Alapismeretek
Változók tulajdonságai
További alapfogalmak
Fordítási egységEl®feldolgozott forrásmodul. Részei:
függvényde�níciókküls® deklarációk
Küls® deklarációMinden fv. testén kívüli deklaráció → küls®/globális változó
Hatwágner F. Miklós Alapismeretek
Változók tulajdonságai
Globális (küls®) változók
Hatásköre: fordítási egységben a deklarációtól a modul végéig(fájl/globális hatáskör)
Élettartam: teljes futásid® (statikus élettartam)
Memóriaterület: fordítási id®ben, els®dleges adatterületen
Alapértelmezett kezd®érték: minden bit zérus
Alapértelmezett tárolási osztály: extern
extern explicit használata → nincs memóriafoglalás!
Azonos nev¶ lokális változó �elfedi�
modul1.c
extern int i;extern char s[];/* ... */
modul2.c
int i;char s[64];/* ... */
Hatwágner F. Miklós Alapismeretek
Változók tulajdonságai
pelda12.c, els® rész
/* PELDA12.C -- A leghosszabb szövegsor kiválasztása */
#include <stdio.h>
#define MAXLINE 1000 /* A beolvasott sor max. hossza */
char line[MAXLINE+1]; /* Az aktuális sor */
char save[MAXLINE+1]; /* Az aktuális max. sor */
int max; /* Az aktuális max. sor hossza */
int getline(void);
void copy(void);
void main(void) {
int len; /* Az aktuális sor hossza */
printf("A leghosszabb szövegsor kiválasztása\n");
printf("A sorokat zárja le Enter-rel!\n");
printf("Utoljára adjon meg egy üres sort vagy Ctrl+Z-t!\n\n");
max = 0;
while((len=getline()) > 0)
if (len>max) { max=len; copy(); }
printf("A leghosszabb sor:\n");
if(max > 0) printf("\n%s\n",save); } /* Volt sor */
Hatwágner F. Miklós Alapismeretek
Változók tulajdonságai
pelda12.c, második rész
int getline(void) {
/* MAXLINE méret¶ karakterlánc beolvasása line-be.
A függvény a karakterlánc hosszát adja vissza.
line tömbnek MAXLINE+1 méret¶nek kell lennie. */
int c, i;
for(i=0; i<MAXLINE && (c=getchar())!=EOF && c!='\n'; ++i)
line[i]=c;
line[i] = '\0';
return(i);
}
void copy(void) {
/* line másolása save-be. save-t elég nagynak tételezi fel */
int i;
i = 0;
while((save[i]=line[i]) != '\0') ++i;
}
Hatwágner F. Miklós Alapismeretek
Változók tulajdonságai
Globális változók használata
+ fv. paraméter átadása megtakarítható
− nehezen újrahasznosítható fv.-ek: küls® változókat is vinni kell→ lehetséges névegyezések ↔ csak lokális változók és fv.paraméterek esetén nincs ilyen gond
− nehezebben áttekinthet®, karbantartható program
Hatwágner F. Miklós Alapismeretek
Inicializálás
Kezd®értékadás deklarációban.
Statikus élettartam: program indulásakor, konstans kifejezéssel
Lokális élettartam: minden létrejövetelkor, bármilyen legáliskifejezéssel
típus azonosító<=inicializátor>;típus tömbazonosító[<méret>]<=inicializátorlista>;, aholtípus ≡ <tárolási-osztály><típusmódosító><alaptípus>
Az inicializátor egy hozzárendelés-kifejezés (→ típusok,konverziók)
Tömböknél:
inicializátorlista elemszáma ≤ tömb elemszáma
Ha inicializátorlista elemszáma < tömb elemszáma → továbbielemek nullázódnak
Ha <méret>-et nem speci�kálták, megállapítjákinicializátorlista elemszámából
Hatwágner F. Miklós Alapismeretek
Inicializálás
De�níció, hozzárendelés
char k, j;
k = 'b';
int i;
i = 42;
float ftomb[3];
ftomb[0] = 1.; ftomb[1] = 2.;
ftomb[2] = 3.;
int itomb[3];
itomb[0] = itomb[1] =
itomb[2] = 0;
char ctomb[4];
ctomb[0] = 'Z'; ctomb[1] = 's';
ctomb[2] = 'u'; ctomb[3] = '\0';
Inicializálás
char k='b', j;
int i = 42;
float ftomb[3] = {1., 2., 3.};
int itomb[3] = {0};
char ctomb[4] = {'Z', 's', 'u',
'\0'}
char ctomb2[] = "Zsu";
Hatwágner F. Miklós Alapismeretek