K&R ANSI C: Rozwiązanie ćwiczeń 5.3 i 5.4
Poprzednio zaprezentowałem rozwiązanie ćwiczenia 3.3. Teraz czas na kolejne.
Zadania są podobnego typu, ponieważ znów są na temat operacji na stringach, ale czy takie zadania nie są jednymi z najciekawszych?
Ćwiczenia 5.3. Napisz wskaźnikową wersję funkcji strcat z rozdziału 2. (strcat(s,t) kopiuje ciąg t na koniec ciągu s).
void strcat(char *s, char *t)
{
while(*s++);
s--;
while(*s++=*t++);
}
Pętle while wykorzystują fakt że symbol końca stringu ' ’ jest interpretowany jako wartość 0 czyli jako fałsz. Co powoduje, że wskaźnik związany z stringiem s po pętli ląduje o jeden dalej niż ' ’ przez co trzeba cofnąć się o jeden znak. Co ważne pętle while nie posiadają żadnych instukcji w sobie więc pętlę trzeba zakończyć średnikiem.
Potem następuje kopiowanie danych przez drugiego while’a, kopiowany też jest znak zakończenia stringa z dodawanego stringa.
Przy korzystaniu z tej funkcji w swoim programie potrzebna jest zmiana nazwy funkcji, ponieważ funkcja jest jest już zdefiniowana w bibliotece standardowej. Błąd o istniejącej już funkcji będzie się pojawiał nawet gdy nie podamy w #include <string.h>.
Ćwiczenie 5.4 Napisz funkcję strend(s,t), która zwraca 1, jeżeli ciąg t zostanie znaleziony na końcu ciągu s, lub 0.
int strend(char *s, char *t)
{
int t_len = strlen(t);
while(*s++); s--;
while(*t++); t--;
for(;(t_len >= 0)&&(*s--==*t--); t_len--);
if(t_len >= 0)
return 0;
else
return 1;
}
W tej funkcji wykorzystuje strlen (funkcja zdefiniowana w <string.h>) do pozyskania długości dodawanego stringu – ta wartość będzie użyteczna później.
Dwa while służą do przesunięcia wskaźnika na koniec stringu, ten sam trick co w poprzedniej funkcji.
Pętla for nie przypisuje żadnej wartości do żadnej zmiennej więc pierwsze pole jest puste. Warunek jest podzielony na dwa pod-warunki.
- t_len>=0 sprawdza czy został całkowicie sprawdzony ciąg t
- *s–==*t– sprawdzenie kolejnych znaków i jednocześnie przesunięcie wskaźnika o jedną pozycję do tyłu. Ponieważ sprawdzamy czy t znajduje się na końcu s, zaczynając od końca ciągu s.
Funkcja for nie posiada w sobie żadnych instrukcji więc potrzebny jest średnik na końcu linii z forem.
Prawidłowo zmienne t_len powinna być mniejsza od zera, gdy wskaźnik przeszedł przez cały ciąg t, w każdym innym przypadku gdzieś na drodze wystąpił błąd w porównywaniu.