You are on page 1of 14

Strukture

Strukture

Strukturirani (sloeni) tip podataka


koji definie korisnik

Razlike u odnosu na niz


kod niza istorodne komponente - zasebni
objekti, identifikuju se indeksima
vrednost funkcije ne moe da bude niz
(moe pokaziva)

sastoji se od vie komponenti


komponente imaju identifikatore
ne moraju biti istog tipa
struktura se smatra jednim objektom
(moe biti i vrednost funkcije)

Koristi se za sloene objekte


logiki povezane informacije

Strukture

Strukture
Definicija naredbom struct + ime + opis

komponente

struct tacka
{int x, y;} a, b, c;

vidljive samo unutar strukure kojoj


pripadaju

struct pravougaonik
{struct tacka dole_levo, gore_desno;};

mogu ista imena u razliitim


strukturama

struct krug
{double r; struct tacka centar;};

mogu ista imena kao promenljive


1

Strukture

Strukture

definisanje promenljivih ovog tipa

dodela poetnih vrednosti

mogue pozvati se na ranije definisanu


strukturu
(za poziv na tip mora: struct + identifikator
strukture - kao kod enum)

niz vrednosti unutar zagrada


(kao kod niza)
konstantni izrazi
dodeljuju se sukcesivnim komponenatama
strukture
broj i tipovi vrednosti moraju da se slau sa
komponentama, vie vrednosti nije dozvoljeno
ako je manje vrednosti, preostale komponente
se inicijalizuju nulama

dati njen opis direktno


(moe se izostaviti identifikator strukture)

Strukture

Strukture

dodela poetnih vrednosti


mogu se definisati i nizovi struktura

u obliku izraza
koji predstavlja poziv funkcije
koja je tipa te strukture

ako se sa typedef
definie strukturni tip,
njegov identifikator se moe
koristiti kao oznaka tipa
i bez slubene rei struct

struct tacka p = {35, -12}, q;


struct pravougaonik w, x, y = {{1, 1},
{3, 3}};
2

Strukture

Upotreba struktura

typedef struct {char ime[16], prezime[16];} ime;

dozvoljena dodela vrednosti (=)


za promenljive istog strukturnog tipa

typedef struct {
char dan, mesec; short int godina;
} datum;
typedef struct {
char maticni_broj[13];
ime osoba;
datum datum_rodjenja;
char adresa[30];
} gradjanin;

prepiu se sve komponente

gradjanin g1, g2, g3;

Upotreba struktura

Upotreba struktura

Primer:

dve strukturne promenjive


su istog tipa ako:

a i b razliitog tipa imaju isti opis


su definisane istom naredbom
struct {int x,y;} a;
struct {int x,y;} b;

za njihovu definiciju se koristi


isti identifikator tipa

Upotreba struktura

Upotreba struktura

mogua primena adresnog operatora,


kao i pokazivai na strukture

kako niz ne moe biti vrednost funkcije,


moe struktura sa nizom kao jednom
komponentom

struct krug *p;

od struktura mogu da se prave nizovi

struktura moe biti i

veliina strukture se dobija sa sizeof


(ne mora da bude zbir komponenti ako
postoje neka ogranienja u smetanju)

argument funkcije (po vrednosti)


kao i vrednost funkcije

Upotreba struktura

Upotreba struktura

za pristup komponentama se koristi


binarni operator taka (.)
a.x
(*p).r

a.x=13; a.z=-22;
a={13,-22} (samo inicijalizacija !!!)

(zagrade su neophodne !!!)

x.dole_levo.x=4; x.dole_levo.y=-5;
x.gore_desno.x=7; x.gore_desno.y=0;
w.dole_levo=a; w.gore_desno=p;

zbog iste upotrebe pokazivaa na


strukture - binarni operator ->
p->r

Upotreba struktura

Upotreba struktura
/* definisanje tipa Tacka */

/* izraunavanje rastojanja izmeu taaka */


struct tacka {int x,y;};
typedef struct tacka Tacka;

#include <math.h>

/* formiranje take od zadatih komponenti*/

double rastojanje (Tacka g, Tacka h) {


return sqrt(pow(g.x-h.x,2)+pow(g.y-h.y,2));
}

Tacka pravi_tacku (int x, int y) {


Tacka t;
t.x=x;
t.y=y;
return t;
}
...

const Tacka NULA = {0,0};


...

Upotreba struktura

Dinamike strukture podataka


strukture pogodne za formiranje
sloenih dinamikih struktura
podataka (promenljiva i veliina i
logika povezanost)

/* nalaenje take najblie koordinatnom poetku */


Tacka * najbliza(Tacka a[], int n) {
Tacka *min = a;
double r = rastojanje(a[0],NULA), s;
for (int i=1; i<n; i++) {
s = rastojanje(a[i],NULA);
if (s<r) {r=s; min=a+i;}
}
return min;
}

obino se sastoje od korisnog


sadraja i pokazivaa na druge
objekte
5

Dinamike strukture podataka

Dinamike strukture podataka

Primer linearne liste za


predstavljanje nizova objekata

definicija mogua jer je


u trenutku deklaracije pokazivaa,
identifikator strukture
je ve definisan

dinamiko stvaranje, brisanje,


preureivanje objekata u listi

typedef struct element {


int broj;
struct element *sled ;
} Element;

nemogua "rekurzivna" definicija


kada je komponenta strukture
sama ta struktura

sled - pokaziva na naredni lan liste

Dinamike strukture podataka

Dinamike strukture podataka

Linearna lista

dodavanje, brisanje i ureivanje


elemenata iskazuje podeavanje
pokazivaa

typedef struct element {


int broj;
struct element *sled ;
} Element;

nedostaci:
dodatni prostor za pokazivae
samo sekvencijalan ali ne i direktan
pristup

Element *niz;
sled - pokaziva na naredni lan liste
niz pokaziva na poetak liste
6

Dinamike strukture podataka

Dinamike strukture podataka

Druga primena - binarno stablo

struct Cvor {
int broj;
struct Cvor *levi, *desni;
} *stablo;

koren i dva podstabla


moe da se definie rekurzivno
jer je bilo koji podskup
povezanih vorova - stablo

stablo - pokaziva na koreni vor


bolje definisati sa typedef
kao u primeru sa listom

Unije

Unije
naredba union
(sintaksa kao za struct)

strukturirani tipovi
koji omoguavaju da se u
isti memorijski prostor
smetaju podaci razliitih tipova u
razliitim vremenskim intervalima

struct {
int i;
double d;
char *c;
} s;
7

union {
int i;
double d;
char *c;
} u;

Unije

s: s.i

s.d

s.c

Unije
za razliku od strukture,
u jednom momentu
samo jedna komponenta
ima definisanu vrednost

u: u.i
u.d
u.c

sizeof s

sizeof u

veliina odreena najveom


komponentom

Polja bitova

Unije

struktura
ije su komponente
duine nekoliko bitova
(pakuju se na mainski zavisan nain)

programer treba da vodi rauna


o konzistentnom korienju
komponenti
(posledice su nepredvidive
ako se upie u jednu,
a koristi druga komponenta)

esto za opisivanje hardverskih registara


programi koji koriste polja bitova su
obino mainski zavisni
8

Polja bitova

Polja bitova
deklaracija

Standard ne definie:
da li polje bitova moe da bude due od
mainske rei

kao za strukturne tipove

da li komponenta moe da bude dua od


mainske rei

sve komponente moraju da budu


unsigned int

da li komponenta moe da prelazi granicu rei

duina polja se navodi u bitovima

da li se reaju zdesna ili obrnuto

Polja bitova

Jednostruko ulanane liste

struct {
unsigned int n:1, z:1, prio:4;
} status_reg;

lst:

typedef struct elem {


int broj;
struct elem
*sled;
} Elem;

status_reg.prio=5;
if (status_reg.n != 1 &&
status_reg.z != 0) ...
9

NULL

Obilazak liste odreivanje


broja elemenata

Obilazak liste ispisivanje svih


elemenata

int duz (Elem *lst) {


Elem *tek;
int n = 0;
for (tek=lst; tek; tek=tek->sled)
n++;
return n;
}

void pisi (Elem *lst) {


Elem *tek;
for (tek=lst; tek; tek=tek->sled)
printf ("%d ", tek->broj);
printf ("\n");
}

Dodavanje novog elementa na


poetak liste

Dodavanje novog elementa na


kraj liste
Elem *na_kraj (Elem *lst, int b) {
Elem *tek, *novi = malloc (sizeof(Elem));
novi->broj = b;
novi->sled = NULL;
if (!lst)
lst = novi;
else {
for (tek=lst; tek->sled; tek=tek->sled);
tek->sled = novi;
}
return lst;
}

Elem *na_pocetak (Elem *lst, int b) {


Elem *novi = malloc (sizeof(Elem));
novi->broj = b;
novi->sled = lst;
lst = novi;
return lst;
}
10

Umetanje elementa u rastue


ureenu listu

Sortiranje liste metodom izbora

Elem *umetni (Elem *lst, int b) {


Elem *tek = lst, *pret = NULL, *novi;
while (tek && tek->broj < b) {
pret = tek;
tek = tek->sled;
}
novi = malloc (sizeof(Elem));
novi->broj = b; novi->sled = tek;
if (!pret)
lst = novi;
else
pret->sled = novi;
return lst;
}

void uredi (Elem *lst) {


Elem *i, *j; int p;
for (i=lst; i; i=i->sled)
for (j=i->sled; j; j=j->sled)
if (j->broj < i->broj) {
p = i->broj;
i->broj = j->broj;
j->broj = p;
}
}

Izostavljanje elemenata sa
datom vrednou (1)

Brisanje svih elemenata liste


void brisi (Elem *lst) {
Elem *stari;
while (lst) {
stari = lst;
lst = lst->sled;
free (stari);
}
}

Elem *izostavi (Elem *lst, int b) {


Elem *tek = lst, *pret = NULL,
*stari;
while (tek)
if (tek->broj != b) {
pret = tek;
tek = tek->sled; }
11

Izostavljanje elemenata sa
datom vrednou (2)

Dvostruko ulanane liste

else { /* ako se element izostavlja */


stari = tek;
tek = tek->sled;
if (!pret)
lst = tek;
else
pret->sled = tek;
free (stari);
}
return lst;
}

prvi:

NULL

NULL

:posl

typedef struct elem {


int broj;
struct elem *sled, *pret;
} Elem;
typedef struct {
Elem *prvi, *posl } Lista;

Prazna lista i
obilazak liste

Ispisivanje liste u napred

Prazna lista: oba pokazivaa su NULL


Lista lst = {NULL, NULL};
Obilazak u napred:
for (tek=lst.prvi; tek; tek=tek->sled)
{}
Obilazak u nazad:
for (tek=lst.posl; tek; tek=tek->pret)
{}

void pisi_unapred (Lista lst) {


Elem *tek;
for (tek=lst.prvi; tek; tek=tek->sled)
printf ("%d ", tek->broj);
printf ("\n");
}

12

Nalaenje prve pojave broja

Ispisivanje liste u nazad


void pisi_unazad (Lista lst) {
Elem *tek;
for (tek=lst.posl; tek; tek=tek->pret)
printf ("%d ", tek->broj);
printf ("\n");
}

Elem *nadji_prvi (Lista lst, int b) {


Elem *tek;
for (tek=lst.prvi; tek; tek=tek->sled)
if (tek->broj == b) return tek;
return NULL;
}

Dodavanje na poetak

Nalaenje poslednje pojave broja


Elem *nadji_posl (Lista lst, int b) {
Elem *tek;
for (tek=lst.posl; tek; tek=tek->pret)
if (tek->broj == b) return tek;
return NULL;
}

void na_pocetak (Lista *plst, int b) {


Elem *novi = malloc (sizeof(Elem));
novi->broj = b;
novi->sled = plst->prvi;
novi->pret = NULL;
if (! plst->posl) plst->posl = novi;
else
plst->prvi->pret = novi;
plst->prvi = novi;
}
13

Dodavanje na kraj

Brisanje svih elemenata

void na_kraj (Lista *plst, int b) {


Elem *novi = malloc (sizeof(Elem));
novi->broj = b;
novi->pret = plst->posl;
novi->sled = NULL;
if (! plst->prvi) plst->prvi = novi;
else
plst->posl->sled = novi;
plst->posl = novi;
}

void brisi (Lista *plst) {


Elem *tek = plst->prvi, *stari;
while (tek) {
stari = tek;
tek = tek->sled;
free (stari);
}
plst->prvi = plst->posl = NULL;
}

Izostavljanje prve pojave broja

Izostavljanje poslednje pojave


broja

void izostavi_prvi (Lista *plst, int b) {


Elem *tek = nadji_prvi (*plst, b);
if (tek) {
if (! tek->pret) plst->prvi = tek->sled;
else
tek->pret->sled = tek->sled;
if (! tek->sled) plst->posl = tek->pret;
else
tek->sled->pret = tek->pret;
free (tek);
}
}

void izostavi_posl (Lista *plst, int b){


Elem *tek = nadji_posl (*plst, b);
if (tek) {
if (! tek->pret) plst->prvi = tek->sled;
else
tek->pret->sled = tek->sled;
if (! tek->sled) plst->posl = tek->pret;
else
tek->sled->pret = tek->pret;
free (tek);
}
}
14

You might also like