Am vazut ca tablourile ne permit memorarea unor date omogene. O structura este un tip de data care ne permite gruparea unor elemente eterogene. Este o colectie de una sau mai multe variabile, grupate sub un singur nume. Vom implementa in continuare un tip de data care reprezinte o data calendaristica. Pentru a fi cunoscuta de compilator, o structura trebuie sa fie mai intii definita : astfel compilatorul va sti necesarul de memorie pentru alocare si va identifica cimpurile structurii.
struct data {
int luna;
int zi;
int an;
};
Astfel am declarat un nou tip de date numit data. Aceasta structura este o definitie pentru compilator: nu se aloca spatiu si nu poate fi utilizata ca o variabila. Deci, de fapt, apare un nou cuvint-cheie, utilizat in declararea de variabile.
struct data zi;
defineste o variabila numita zi ca fiind de tip data.
Se poate utiliza declaratia typedef pentru a se lucra mai comod.
typedef struct data {
int luna;
int ziua;
int an;
}DATA;
DATA zi;
Initializare :
struct data zi={5,4,1997};
DATA zi1={6,19,1998};
Accesul la membrii unei structuri se face prin operatorul punct '.'.
DATA zi; zi.luna = 6; zi.ziua = 19; zi.an = 1998;
Pointeri catre structuri
Un pointer catre o structura se declara similar cu pointerii catre variabilele simple :
struct data *pzi;
DATA zi_nou={6,19,1998};
Prin initializarea
pzi=&zi_npu;
pzi va contine adresa structurii zi_nou.
pzi -> luna = 14; pzi -> ziua = 3; pzi -> anul = 2000;
Accesul la membrii unei structuri, prin intermediul unui pointer, se face cu -> .
Structuri si functii .
O structura poate fi trimisa unei functii in trei moduri :
Functiile pot intoarce :
O lista inlantuita este o structura complexa, foarte folositoare in multe aplicatii. O lista inlantuita se compune dintr-o serie de noduri, fiecare nod continind o parte de informatie si o parte de legaturi.
-------- -------- | date | --->| date | |--------| | |--------| | pointer|---- | pointer| ---> NULL -------- --------
O structura care contine un element de date si o legatura (pointer) catre nodul urmator este creata prin:
struct list {
int n;
struct list *next;
};
Aceasta defineste o noua strutura de date numita list (definitia unui nod). Primul element este un intreg numit n, iar cel de-al doilea ,next, este un pointer la o alta structura (sau nod). Fie doua noduri de acelasi tip :
struct list nod1, nod2;
Pointerul next al structurii nod1 poate fi initializat sa indice structura nod2
nod1.next = &nod2;
ceea ce realizeaza o legatura intre cele doua structuri.
#include <stdio.h>
struct list {
int n;
struct list *next;
};
main()
{
struct list s1, s2, s3;
int i;
s1.n = 100;
s2.n = 200;
s3.n = 300;
s1.next = &s2;
s2.next = &s3;
i = s1.next->n;
printf("%d\n", s2.next->n);
}
Sa consideram urmatoarele atribuiri :
s1.next = s2.next /* rupe legatura intre s1 si s2; s2 "dispare" din lista */ s2_3.next = s2.next; /*adauga structura s2_3 la lista*/ s2.next = &s2_3;
Variabilele tipului enumerat pot primi numai valori care au fost declarate anterior.
enum luni_an { ian = 1, feb, mar, apr, mai, iun, iul, aug, sep, oct, nov, dec };
enum luni_an luna;
luna = feb;
In declaratia anterioara, luna este declarata ca fiind de tip enumarat. Ian primeste valoarea 1, feb 2 etc. Luna nu poate primi vreo valoare din afara domeniului de valori.
Acesta este un tip special de date care se aseamana cu structura dar este foarte diferit: poate contine la momente de timp diferite obiecte de tipuri diferite. Practic este vorba de mai multe variabile suprapuse in aceeasi zona de memorie. Declaratia este :
union tip {
char c;
float f;
int n;
};
union tip v;
Am declarat o variabila v de tip uniune. Toate operatiile permise la structuri sunt permise si la uniuni. Structura este suficient de mare ca sa contina cel mai mare membru.
Astfel variabila v poate fi fie un caracter, un float sau un intreg la un moment dat. Limbajuk C tine minte ceea ce este v la un moment dat, dar nu pune la dispozitie nici un mecanism pentru programator pentru a preveni accesul incorect.
Cimpurile de biti apar in structuri in care se specifica numarul de biti pe care este reprezentata fiecare variabila (tip intreg). Cimpurile de biti sunt utile pentru dispozitive de intrare/iesire (acces la nivel de bit) :
struct cimp {
unsigned a: 1;
unsigned b: 3;
unsigned : 4;
unsigned c : 3;
unsigned d : 2;
}s;
s.a se reprezinta pe un bit, s.b se reprezinta pe trei biti etc.
Metoda ne usureaza munca cu elemente la nivel de bit, care altfel ar trebui sa le prelucram prin operatii logice si deplasari.