Capitolul 5.5. Pointeri pe caractere si functii

Vezi subiectul anterior Vezi subiectul urmator In jos

Capitolul 5.5. Pointeri pe caractere si functii

Mesaj  zooky la data de Mier Mar 18, 2009 1:47 pm

Un sir constant scris astfel

"I am a string "

este un tablou de caractere. In reprezentare interna, compilatorul termina un tablou cu caracterul \0 in asa fel incit programele sa poata detecta sfirsitul. Lungimea in memorie este astfel mai mare cu 1 decit numarul de caractere cuprinse intre ghilimele.
Poate cea mai comuna aparitie a unui sir de constante este ca argument al functiei cum ar fi in

char *message;

atunci instructiunea

message = "now is the time";

asigneazaa lui mesage un pointer in functie de caracterele reale. Aceasta nu este o copie a sirului; nu sint implicati decit pointerii. C nu este inzestrat cu alti operatori care sa trateze eze un sir de caractere ca o unitate.
Vom ilustra mai multe aspecte in legatura cu pointerii si cu tablourile stiind ca doua functii cu adevarat utile, din biblioteca standard de I/O, subiect care va fi discutat in capitolul 7.
Prima functie este strcpy(s, t) care copiaza sirul t in sirul s. Argumentele sint scrise in aceasta ordine prin analogie cu aranjarea, unde cineva ar putea spune

s = t

pentru a asigna pe t lui s. Versiunea ca tablouri este mai intii.

strcpy(s, t) /*copiaza t in s */
char s[], t[];
{
int i;
i = 0;
while ((s[i] = t[i] != '\0')
i++;
}

Iata o versiune a lui strcpy cu pointeri

strcpy(s, t) /* copiaza t in s, versiunea pointeri 1*/
char *s, *t;
{
while ((*s = *t) != '\0') {
s++;
t++;
}
}


Deoarece argumentele sint transmise prin valoare, strcpy poate utiliza s si t in orice fel se doreste. Aici ei sint conventional utilizati ca pointeri, care parcurg tablourile pina in momentul in care s-a copiat \0 sfirsitul lui t, in s.
In practica, strrcpy nu va fi scris asa cum s-a aratat mai sus. O a doua posilitate ar fi

strcpy(s, t) /* copiaza t in s, versiunea 2*/
char *s, *t;
{
while ((*s++ = *t++) != '\0')
;
}

In aceasta ultima versiune se imita incrementarea lui s si t in partea de test. Valoarea lui *t++ este caracterul pe care a pointat inainte ca t sa fi fost incrementat; prefixul ++ nu-l schimba pe t inainte ca acest caracter sa fi fost adus. In acelasi fel, caracterul este stocat in vede a pozitie s inainte ca s sa fie incrementat. Acest caracter este deasemenea valoarea care se grupeaza cu \0 pentru simboul buclei. Efectul net este ca, caracterele sint copiate din t in s, inclusiv sfirsitul lui \0.
Ca o ultima abreviere vom observa ca si gruparea cu \0 este redundanta, astfel ca functia este adesea scrisa ca

strcpy(s, t) /* copiaza t in s; versiunea pointeri 3 */
char *s, *t;
{
while (*s++ = *t++)
;
}

Desi aceasta versiune poate parea compilcata la prima vedere, aranjamentul ca notatie este considerat suveran daca nu exista alte ratiuni de a schimba astfel ca il veti intilni frecvent in programele C.

A doua rutina este strcmp(s, t) care compara sirurile de caractere s si t si returneaza negativ, zero sau pozitiv in functie de relatia dintre s si t; care poate fi: s<t, s=t sau s>t. Valoarea returnata este obtinuta prin scaderea caracterului de pe prima pozitie unde s difera de t.

strcmp(s, t)
/* returneaza <0 daca s<t, 0 daca s==t, >0 daca s>t */
char s[], t[];
{
int i;
i = 0;
while (s[i] == t[i])
if (s[i++] == '\0')
return(0);
return(s[i] - t[i]);
}

Versiunea pointeri a lui strcmp.

strcmp(s, t) /* returneaza <0 daca s<t, 0 daca s==t,
>0 daca s>t */
char *s, *t;
{
for ( ; *s == *t; s++, t++)
if (*s == '\0')
return(0);
return(*s - *t);
}

Daca ++ si -- sint folositi altfel decit operatori prefix sau postfix pot apare alte combinatii de * si ++ si --, desi mai putin frecvente. De exemplu:

*++p

incrementeaza pe p inainte de a aduce caracterul pe care pointeaza
p.

*--p

decrementeaza pe p in acelasi conditii.

Exercitiul 5.2. Scrieti o versiune pointeri pentru o functie strcat expusa in capitolul 2: strcat(s, t) copiaza sirul t la sfirsitul sirului s.

Exercitiul 5.3. Scrieti un macro pentru strcpy.

Exercitiul 5.4. Rescrieti variantele programelor din capitolele anterioare si exercitii cu pointeri in loc de tablouri indexate. Bune posibilitati ofera: getline, atoi, itoa si variantele lor, reverse, index, getop.
avatar
zooky
Moderator
Moderator

Numarul mesajelor : 147
Data de inscriere : 15/03/2009
Varsta : 24
Localizare : Cernatesti City

Vezi profilul utilizatorului http://e-learning.forumhit.ro

Sus In jos

Vezi subiectul anterior Vezi subiectul urmator Sus


 
Permisiunile acestui forum:
Nu puteti raspunde la subiectele acestui forum