STRINGOVI U JEZIKU C
String u jeziku C predstavlja niz podataka tipa char i služi za rad sa tekstom.
Definišu se na sledeći način:
char tekst[] = "Ovo je neki tekst";
ili, može i ovako:
char tekst[] = {'O', 'v', 'o', ' ', 'j', 'e', 'n', 'e', 'k', 'i',
' ', 't', 'e', 'k', 's', 't', '\0'};
Objašnjenje null karaktera
U jeziku C, string je niz karaktera koji je uvek terminiran specijalnim karakterom
'\0' (null karakter). Ovaj karakter označava kraj stringa, pa kada radimo sa
stringovima u C-u, funkcije kao što su printf ili strlen prestaju
da čitaju znakove kada naiđu na '\0'. Bez ovog karaktera, funkcije ne bi mogle
ispravno odrediti gde string završava.
Na primer, ako definišemo niz karaktera bez '\0', funkcija
printf može nastaviti da ispisuje podatke iz memorije, sve dok slučajno
ne naiđe na neki '\0'. To može dovesti do nepredvidivih rezultata.
Zato je veoma važno da stringovi uvek budu pravilno terminisani.
Preciznost u primerima
Kada definišemo string u C-u, možemo koristiti dve metode. Prva, jednostavna metoda je:
char tekst[] = "Ovo je neki tekst";
Ova definicija automatski dodaje null karakter '\0' na kraj stringa.
Drugi način, ručno definisanje stringa kao niza karaktera, izgleda ovako:
char tekst[] = {'O', 'v', 'o', ' ', 'j', 'e', ' ', 'n', 'e', 'k', 'i',
' ', 't', 'e', 'k', 's', 't', '\0'};
Tip podatka char
Tip podatka char je sličan int podatku, tj. služi za opis celih
brojeva, ali zauzima samo 8 bita memorije, za razliku od int-a, koji zauzima
16 ili 32 bita i može čuvati veći broj.
Tip char se obično koristi za čuvanje znakovnih podataka, odnosno njihovih kodova.
Tako, na primer, ako želimo da sačuvamo slovo A u memoriji, čuvali bi zapravo
kod slova A. Kodovi karaktera (znakova) su pridruženi brojevi, pomoću kojih razlikujemo karakter.
Npr. kod slova A je broj 65, kod slova B je 66 itd.
Vrednost koda možemo dobiti ako karakter stavimo pod apostrofe, npr. 'A'.
Primer definisanja koda slova A i njegovo ispisivanje, zajedno sa ispisivanjem karaktera, bi bio:
char ch = 'A';
printf("Kod slova i slovo: %c %d\n", ch, ch);
Posle pokretanja:
Kod slova i slovo: A 65
Detaljno objašnjenje char tipa u C jeziku
Tip podatka char koristi se za predstavljanje pojedinačnih karaktera. Njegove glavne karakteristike su:
- Veličina i vrednosti: Zauzima 1 bajt memorije (8 bita) i može sadržati vrednosti od -128 do 127 (za
signed char) ili od 0 do 255 (zaunsigned char). - Kodiranje: Obično koristi ASCII kod za mapiranje karaktera na brojeve. Na primer,
'A'je 65,'a'je 97. - Operacije: Može se koristiti u aritmetičkim operacijama, jer se karakteri interno čuvaju kao numeričke vrednosti.
Praktični primer
#include <stdio.h>
int main() {
char c = 'A';
printf("Character: %c, ASCII value: %d\n", c, c);
return 0;
}
Razlike između char i stringova:
Pojedinačni karakter (char) i niz karaktera (string) se razlikuju – stringovi zahtevaju niz
char-ova sa završnim karakterom \0.
Primer 1: Ispisivanje tablice ASCII kodova karaktera
Ispisaćemo kodove karaktera tako što, koristeći for petlju, menjamo kodove od 32 do 126
i te vrednosti ispisujemo koristeći konverziju "%c" za ispis karaktera,
a "%d" za ispis koda odgovarajućeg karaktera.
Napomena: Kod 127 i kodovi od 0–32 postoje i odnose se na neštampajuće znake, kontrolne i bele znakove. Postoje i znaci sa kodovima većim od 127 a manjim ili jednakim 255 i oni zavise od lokalnih podešavanja (npr. ćirilična slova u određenim područjima).
#include <stdio.h>
#include <stdlib.h>
int main() {
for(int ch = 32; ch <= 126; ch++) {
printf("%c %d\n", ch, ch);
}
return 0;
}
Posle izvršenja programa vidimo sledeće:
! 33
" 34
# 35
$ 36
% 37
...
~ 126
Učitavanje znakova sa tastature
Učitavanje jednog karaktera (znaka) sa tastature, uključujući i beli znak, može se izvršiti pomoću funkcije
getchar() iz zaglavlja <stdio.h>.
U istom zaglavlju se nalazi i funkcija koja će ispisati ovaj znak – putchar(ch), gde je ch taj znak.
Funkcije poput getchar(), putchar() i funkcije iz zaglavlja <ctype.h> omogućavaju
jednostavno upravljanje ulazom i izlazom podataka, kao i ispitivanje karaktera:
- getchar() – omogućava unos jednog karaktera sa tastature.
- putchar() – omogućava ispis jednog karaktera na ekranu.
- <ctype.h> – sadrži funkcije za proveru tipa karaktera (da li je slovo, cifra, beli znak, itd.), što pomaže u validaciji i obradi unosa.
Ispitivanje znakova pomoću funkcija iz <ctype.h>
Najčešće korišćene funkcije su:
isalnum(ch)– da li jechslovo ili cifra?isalpha(ch)– da li jechslovo?islower(ch)– da li jechmalo slovo?isupper(ch)– da li jechveliko slovo?isdigit(ch)– da li jechdecimalna cifra?isspace(ch)– da li jechbeli znak?ispunct(ch)– da li jechznak interpunkcije?iscntrl(ch)– da li jechupravljački znak?
Rezime:
ispunct(ch)vraća true ako je karakter interpunkcijski znak (npr. tačka, zarez, upitnik).isdigit(ch)vraća true ako je karakter cifra (0–9).isalpha(ch)vraća true ako je karakter slovo.islower(ch)vraća true ako je malo slovo.isupper(ch)vraća true ako je veliko slovo.
Ove funkcije omogućavaju jednostavno prepoznavanje vrste karaktera, što je ključno za analizu unosa u mnogim programima.
Primer 2: Analiza unete šifre
Napraviti program koji od korisnika zahteva da unese šifru i ispisuje na ekranu koliko ima malih, velikih slova, cifara i znakova interpunkcije u toj šifri.
Za unos šifre koristićemo do-while petlju i funkciju getchar(), a za ispitivanje vrste znaka funkcije iz zaglavlja <ctype.h>.
#include <stdio.h>
#include <ctype.h>
int main() {
int sc = 0; // broj znakova interpunkcije
int nd = 0; // broj cifara
int uc = 0; // broj velikih slova
int lc = 0; // broj malih slova
char ch;
printf("Unesite šifru!\n");
do {
ch = getchar();
if (ispunct(ch)) {
sc++;
}
if (isdigit(ch)) {
nd++;
}
if (isupper(ch)) {
uc++;
}
if (islower(ch)) {
lc++;
}
} while (ch != EOF && (!isspace(ch) && !iscntrl(ch)));
printf("Šifra ima %d malih slova, %d velikih slova, %d cifru/cifre i %d specijalnih znakova.\n",
lc, uc, nd, sc);
return 0;
}
Učitavanje se vrši sve dok se ne unese beli znak ili neki upravljački znak (npr. novi red), ili se ne unese znak za kraj datoteke (Ctrl+Z).
Izvršenje primera: Na ekranu se vidi broj malih i velikih slova, cifara i interpunkcijskih znakova u šifri koju je korisnik uneo.
EOF i rad sa stringovima i pokazivačima
EOF (End of File) označava signal koji se koristi u programiranju da označi kraj unosa podataka.
U kontekstu funkcije getchar(), kada korisnik unese karaktere, EOF signalizira kraj unosa.
Na primer:
- Ctrl+Z na Windows-u
- Ctrl+D na Unix/Linux sistemima
while petlja u ovom kontekstu omogućava kontinuirani unos dok se ne unese EOF ili beli znak.
Petlja stalno poziva funkciju getchar() i proverava vrednost koju je uneo korisnik, čime omogućava unos više znakova sve dok se ne postigne kraj unosa.
Stringovi i pokazivači
Stringovi u C jeziku predstavljaju nizove podataka tipa char, koji se mogu kreirati i dinamički (pomoću pokazivača) ili statički (kao nizovi).
Definicija dva stringa:
char* pTekst = "Danas je lep dan";
char tekst2[19] = {'A','n','a',' ','v','o','l','i',' ',
'M','i','l','o','v','a','n','a','\0'};
- Dinamičko kreiranje: koristi pokazivač koji pokazuje na konstantni string u memoriji.
- Statičko kreiranje: koristi niz sa unapred određenom veličinom, koji se nalazi na stogu (stack).
Statički string primer:
char tekst2[19] = "Ana voli Milovana";
Ovaj niz zauzima fiksnu memoriju i veličina mu mora biti poznata tokom kompajliranja.
Dinamički string primer:
char* pTekst = "Danas je lep dan";
String se nalazi u memoriji za konstante, a pokazivač pokazuje na njegov prvi karakter.
Pomeranje pokazivača kroz string
Pokazivač pokazuje na određeni element niza. Ako želimo da pređemo na sledeći element, možemo jednostavno uvećati vrednost pokazivača:
pTekst++; // sada pokazuje na sledeći karakter
Više o tome pogledaj u članku: String Pointer in C (Scaler)
Da bismo imali pokazivač na drugi string, možemo dodati sledeći red:
char* pch2 = tekst2; // pokazivač pch2 pokazuje na prvi element niza tekst2
Kompletan kod
#include <stdio.h>
int main() {
// Dinamičko kreiranje stringa pomoću pokazivača
char* pTekst = "Danas je lep dan";
// Pokazivač pokazuje na konstantni string u memoriji.
// Statičko kreiranje stringa pomoću niza
char tekst2[19] = {'A','n','a',' ','v','o','l','i',' ',
'M','i','l','o','v','a','n','a','\0'};
// Ispis stringa kreiranog dinamički
printf("tekst 1:\t");
while (*pTekst != '\0') {
printf("%c", *pTekst); // Ispis trenutnog karaktera
pTekst++; // Pomeri pokazivač na sledeći karakter
}
printf("\n");
// Povezivanje pokazivača sa statičkim nizom
char* pch2 = tekst2;
printf("tekst 2:\t");
while (*pch2 != '\0') {
printf("%c", *pch2); // Ispis karaktera
pch2++; // Pomeri pokazivač na sledeći karakter
}
printf("\n");
return 0;
}
Ciklus se prekida kada se naiđe na karakter '\0'.
Nakon pokretanja programa ispisuju se oba stringa.
Učitavanje stringova u jeziku C
Učitavanje stringa može se izvršiti na više načina:
- Pomoću
getchar()funkcije, znak po znak (kao u prethodnom primeru). - Pomoću
scanffunkcije – učitava se tekst do prvog belog znaka. - Pomoću
fgets()– preporučeni način, jer omogućava bezbedno učitavanje cele linije.
Korišćenje scanf funkcije
char rec[10];
scanf("%s", rec);
Problem sa scanf("%s") je što može doći do prelivanja bafera ako korisnik unese više karaktera nego što niz može da primi.
Da bismo to izbegli, unos treba ograničiti:
scanf("%9s", rec); // Maksimalno 9 karaktera + '\0'
Korišćenje gets i puts funkcija
Funkcija gets() je ranije korišćena za učitavanje celog reda, ali je zastarela i nesigurna, jer može izazvati prelivanje bafera.
Funkcija puts() služi za ispisivanje stringa.
Umesto gets(), preporučuje se upotreba fgets():
fgets(tekst2, sizeof(tekst2), stdin);
Primer 3: Učitavanje stringa
Učitati dva stringa:
- Prvi string – do belog znaka (jedna reč).
- Drugi string – ceo red teksta, sve do znaka za novi red.
#include <stdio.h>
#include <stdlib.h>
int main() {
char tekst1[10], tekst2[50]; // prvi niz manji, drugi veći
// Učitavanje jedne reči pomoću scanf
printf("Unesi tekst (jedna rec):\n");
scanf("%9s", tekst1); // sigurno učitavanje do 9 karaktera
printf("Ucitano: %s\n", tekst1);
getchar(); // da "pojede" Enter sa tastature
// Učitavanje celog reda pomoću fgets
printf("Unesi ceo red teksta:\n");
fgets(tekst2, sizeof(tekst2), stdin);
printf("Ucitano: %s\n", tekst2);
return 0;
}
□ Napomena:
- scanf("%s") se koristi samo za učitavanje jedne reči (do belog znaka).
- fgets() je sigurniji jer omogućava ograničenje broja karaktera i učitava ceo red teksta.
- Funkcija puts() je praktičan način za ispisivanje stringa.
Problemi sa učitavanjem stringova
Problemi koji se javljaju pri učitavanju:
- Zaostali karakter u baferu kada se učitava tekst do belog znaka
- Prelivanje bafera kod učitavanja zastarelom metodom
gets
1. Zaostali karakter u ulaznom baferu
Kada scanf() pročita unos, ostavlja novi red (\n) u ulaznom baferu nakon unete vrednosti.
Ako odmah nakon scanf() koristite funkciju koja čita ceo red, poput fgets(), ona će pročitati preostali \n, što može izgledati kao da korisnik nije uneo ništa.
Rešenje: pozvati getchar() nakon unosa sa scanf().
Poziv getchar() uklanja taj preostali \n iz bafera, omogućavajući pravilno učitavanje sledećeg reda teksta.
a. Korišćenje modifikatora za scanf()
scanf("%s", ime);
b. Korišćenje fgets() i sscanf()
#include <stdio.h>
#include <string.h>
int main() {
char unos[30];
char ime[30];
// Učitava ceo unos
fgets(unos, sizeof(unos), stdin);
sscanf(unos, "%s", ime); // Ekstraktuje prvu reč iz unosa
printf("Prva reč: %s\n", ime);
return 0;
}
c. Ručno uklanjanje znakova iz bafera
int ch;
while ((ch = getchar()) != '\n' && ch != EOF);
d. Upotreba fgets() i obrade stringova
d.1 Primer sa sscanf()
#include <stdio.h>
int main() {
char unos[100];
char ime[30];
printf("Unesite tekst: ");
fgets(unos, sizeof(unos), stdin); // Učitava ceo red, uključujući razmake
if (sscanf(unos, "%s", ime) == 1) {
printf("Prva reč: %s\n", ime);
} else {
printf("Nije uneta validna reč.\n");
}
return 0;
}
d.2 Primer sa strtok()
#include <stdio.h>
#include <string.h>
int main() {
char unos[100];
printf("Unesite tekst: ");
fgets(unos, sizeof(unos), stdin);
unos[strcspn(unos, "\n")] = '\0'; // uklanjanje '\n'
char* token = strtok(unos, " ");
while (token != NULL) {
printf("Reč: %s\n", token);
token = strtok(NULL, " ");
}
return 0;
}
2. Problem sa prelivanjem bafera
Kada se koristi zastarela funkcija gets, dolazi do rizika prelivanja bafera jer funkcija ne ograničava broj učitanih karaktera.
#include <stdio.h>
int main() {
char ime[10];
printf("Unesite ime: ");
gets(ime); // Potencijalno prelivanje bafera
printf("Uneto ime: %s\n", ime);
return 0;
}
Rešenje: koristiti fgets() umesto gets().
fgets(ime, sizeof(ime), stdin);
Poboljšana verzija koda
#include <stdio.h>
#include <string.h>
int main() {
char tekst1[10];
printf("Unesi tekst (do belog znaka):\n");
scanf("%9s", tekst1);
printf("Unesena reč: %s\n", tekst1);
char tekst2[10];
getchar();
printf("Unesi ceo red teksta:\n");
fgets(tekst2, sizeof(tekst2), stdin);
printf("Uneseni tekst: %s\n", tekst2);
char tekst[] = "Priprema za takmičenje iz programiranja";
int poz = 12;
int duzPodstr = 10;
char podstring[duzPodstr + 1];
strncpy(podstring, tekst + poz, duzPodstr);
podstring[duzPodstr] = '\0';
printf("Izdvojeni podstring: %s\n", podstring);
return 0;
}
Određivanje dužine teksta
char tekst[] = "Priprema za takmičenje iz programiranja";
int duzina = strlen(tekst);
printf("Dužina teksta je %d\n", duzina);
Izdvajanje dela teksta iz teksta (Izdvajanje podstringa)
Deo teksta se može izdvojiti iz celog teksta tako što se, upotrebom petlje, prolazi kroz niz podataka tipa
char od pozicije u tekstu odakle treba izdvojiti podstring, pa sve do krajnje željene pozicije.
Tada se tekući znak dodaje u novi niz char podataka, tj. u podstring.
Primer 4: Izdvajanje podstringa
Neka je zadat tekst: "Priprema za takmičenje iz programiranja".
Izdvojiti deo teksta od pozicije 12, dužine od 10 karaktera i ispisati ga na ekranu.
Rešenje sa petljom
#include <stdio.h>
#include <string.h>
int main()
{
char tekst[] = "Priprema za takmičenje iz programiranja";
int duzina = strlen(tekst);
int poz = 12; // podstring počinje od pozicije 12
int duzPodstr = 10;
char podstring[duzina];
for (int c = poz, i = 0; c <= poz + duzPodstr; c++, i++) {
char ch = tekst[c];
podstring[i] = ch;
}
podstring[duzPodstr] = '\0'; // terminator stringa
printf("%s\n", podstring);
return 0;
}
Pozicija c predstavlja poziciju tekućeg karaktera unutar zadatog teksta,
a i je pozicija tekućeg elementa u nizu podstring.
Rešenje pomoću funkcije strncpy()
Zadatak je moguće rešiti i pomoću funkcije strncpy() iz zaglavlja
<string.h>. Ova funkcija kopira deo jednog stringa u drugi,
koji je po dužini manji ili jednak prvom.
#include <stdio.h>
#include <string.h>
int main()
{
char tekst[] = "Priprema za takmičenje iz programiranja";
int duzina = strlen(tekst);
int poz = 12; // podstring počinje od pozicije 12
int duzPodstr = 10;
char podstring[duzina];
strncpy(podstring, tekst + poz, duzPodstr);
podstring[duzPodstr] = '\0'; // dodavanje terminatora
printf("%s\n", podstring);
return 0;
}
Parametri funkcije strncpy():
- 1. parametar – odredište (podstring koji treba dobiti)
- 2. parametar – pokazivač na znak u polaznom tekstu od pozicije
poz - 3. parametar – dužina podstringa
➡ Ostale funkcije iz zaglavlja <string.h> možete pogledati ovde:
cplusplus.com/reference/cstring/
Rešenje sa posebnom funkcijom
Još bolji pristup je da se napravi posebna funkcija za izdvajanje podstringa, koju možemo pozivati više puta za različite delove teksta.
#include <stdio.h>
#include <string.h>
void izdvojiPodstring(char* izvor, char* cilj, int poz, int duzina) {
strncpy(cilj, izvor + poz, duzina);
cilj[duzina] = '\0'; // dodavanje terminatora
}
int main()
{
char tekst[] = "Priprema za takmičenje iz programiranja";
char pod1[20];
char pod2[20];
// Izdvajamo deo od pozicije 12 dužine 10
izdvojiPodstring(tekst, pod1, 12, 10);
printf("Podstring 1: %s\n", pod1);
// Izdvajamo deo od pozicije 0 dužine 9
izdvojiPodstring(tekst, pod2, 0, 9);
printf("Podstring 2: %s\n", pod2);
return 0;
}
Ova funkcija izdvojiPodstring() je univerzalna i može se koristiti
za izdvajanje bilo kog dela teksta, što čini kod preglednijim i fleksibilnijim.
Posle pokretanja:
Pretraga dela teksta unutar većeg teksta
Često je potrebno ispitati da li se neka reč ili neki tekst nalazi u zadatom tekstu i, ako se nalazi, pronaći na kojim pozicijama. Sledeći primer pokazuje jedan način da se ovo uradi.
Primer 5: Pretraga stringa
Proveriti da li i na kojim pozicijama se zadate reči (ana i pera) nalaze u datom tekstu.
Ispisati koliko puta se ponavljaju i na kojim pozicijama, ili ispisati "nije se pojavila" ako se reč ne nalazi u tekstu.
Linearna pretraga za jednu reč
Jedan način je korišćenjem linearne pretrage: prolazi se kroz kompletan tekst znak po znak i poredi se tekući znak sa prvim znakom reči koja se traži. Ako se naiđe na podudaranje prvog znaka, proveravaju se i ostali znakovi. Ako svi znakovi reči odgovaraju, konstatuje se pozicija početka podstringa u tekstu.
#include <stdio.h>
#include <string.h>
int main()
{
char tekst[] = {'a','n','a','v','o','l','i','M','i','l','o','v','a','n','a','\0'};
char rec1[] = "ana";
int brPoj = 0;
int duzTeksta = strlen(tekst);
int duzReci = strlen(rec1);
int poz1 = -1;
int pronasao = 0;
int j = 0;
for(int i = 0; i < duzTeksta; i++) {
char chT = tekst[i];
char ch = rec1[j];
if(!pronasao && chT != ch) {
continue;
}
else if(!pronasao && chT == ch) {
pronasao = 1;
poz1 = i;
while(chT == ch && i < duzTeksta && j < duzReci) {
i++;
j++;
chT = tekst[i];
ch = rec1[j];
}
if(j == duzReci) {
pronasao = 0;
j = 0;
brPoj++;
printf("Pronadjena na %d poz\n", poz1);
}
else {
pronasao = 0;
j = 0;
}
}
}
if(brPoj > 0) {
printf("Rec se pojavila %d puta u tekstu\n", brPoj);
} else {
printf("Ne\n");
}
return 0;
}
U prethodnom kodu se pretraga izvršava samo za reč "ana", a ne za "pera".
U sledećem primeru se koristi dvodimenzioni niz reči i posebna funkcija za pretragu koja vraća poziciju ili -1 ako reč nije nađena.
Pretraga više reči pomoću funkcije
#include <stdio.h>
#include <string.h>
// Funkcija koja vraća poziciju reči u tekstu, ili -1 ako nije pronađena
int pozicijaUTekstu(int poz, char txt[], char rec[]) {
int duzTeksta = strlen(txt);
int duzReci = strlen(rec);
int pronasao = 0;
for(int i = poz + 1, j = 0; i < duzTeksta; i++) {
char chT = txt[i];
char ch = rec[j];
if(!pronasao && chT != ch) {
continue;
}
else if(!pronasao && chT == ch) {
pronasao = 1;
poz = i;
while(chT == ch && i < duzTeksta && j < duzReci) {
i++;
j++;
chT = txt[i];
ch = rec[j];
}
if(j == duzReci) {
break;
} else {
pronasao = 0;
j = 0;
if(i >= duzTeksta) {
poz = -1;
break;
}
}
}
}
return poz;
}
int main() {
char tekst[] = {'a','n','a','v','o','l','i','M','i','l','o','v','a','n','a','\0'};
char rec[2][10] = {"ana", "pera"};
int brPoj = 0;
int poz = -1;
for(int i = 0; i < 2; i++) {
do {
poz = pozicijaUTekstu(poz, tekst, rec[i]);
if(poz != -1) {
brPoj++;
printf("Rec %s Pronadjena na %d poz\n", rec[i], poz);
}
} while(poz != -1);
if(brPoj > 0) {
printf("Rec %s se pojavila %d puta u tekstu\n", rec[i], brPoj);
} else {
printf("Rec %s se nije pojavila u tekstu nijednom\n", rec[i]);
}
brPoj = 0;
poz = -1; // resetuje poziciju pre prelaska na sledeću reč
}
return 0;
}
U ovom kodu:
- Funkcija
pozicijaUTekstu()traži zadatu reč unutar teksta. - Ako se reč pronađe, vraća poziciju njenog prvog karaktera; inače vraća
-1. - Glavna funkcija
main()pretražuje sve reči iz dvodimenzionog nizareci ispisuje rezultate.
Pretraga reči u tekstu – logika i optimizacija
U glavnoj funkciji (main) je zadat dvodimenzionalni niz znakova sa rečima za pretragu i definisani su:
- tekst za pretragu,
- početna pozicija inicijalizovana na
-1, - broj pojavljivanja (
brPoj), čija je početna vrednost nula.
U do-while petlji poziva se funkcija pozicijaUTekstu(), kojoj se prosleđuju:
pozicija, tekst i reč za pretragu.
Funkcija vraća prvu poziciju veću od prethodno pronađene na kojoj se nalazi reč, ili -1 ako reč nije pronađena.
Objašnjenje logike
Zašto se koristi pronasao:
Promenljiva pronasao signalizira trenutak kada se prvi znak reči poklapa sa znakom u tekstu.
Ona omogućava praćenje početka potencijalnog podudaranja i prelazak na detaljnije poređenje narednih znakova.
Kako funkcioniše upoređivanje: Kada se otkrije podudaranje prvog znaka, algoritam koristi petlju za poređenje narednih znakova. Ako se svi znakovi poklope, reč je pronađena. Ako se pojavi razlika, algoritam se resetuje i nastavlja pretragu.
Optimizacija algoritma
Alternativna metoda: KMP algoritam (Knuth-Morris-Pratt). KMP koristi preprocesiranje reči za kreiranje "prefix-suffix" tabele, što omogućava preskakanje nepotrebnih poređenja, značajno ubrzavajući pretragu, posebno za velike tekstove i česte ponavljajuće šablone.
Problemi sa memorijom i dinamička alokacija stringova u C-u
Nepravilno rukovanje stringovima može dovesti do curenja memorije ili prepunjavanja bafera.
Alokacija i promena veličine stringova
char *str = (char *)malloc(50 * sizeof(char));
if (str == NULL) {
printf("Alokacija memorije nije uspela");
return 1;
}
str = (char *)realloc(str, 100 * sizeof(char));
Izbegavanje prepunjavanja bafera
strncpy(str, "Siguran string", 49);
str[49] = '\0'; // Osigurajte završni null karakter
Oslobađanje memorije
free(str);
str = NULL;
Napredni primer: Dinamička konkatenacija stringova
Primer funkcije koja dinamički spaja stringove:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
char *concat(const char *s1, const char *s2) {
size_t len1 = strlen(s1), len2 = strlen(s2);
char *result = (char *)malloc((len1 + len2 + 1) * sizeof(char));
if (!result) {
printf("Alokacija memorije nije uspela");
exit(1);
}
strcpy(result, s1);
strcat(result, s2);
return result;
}
int main() {
char *pozdrav = concat("Zdravo, ", "Svete!");
printf("%s\n", pozdrav);
free(pozdrav);
return 0;
}
U ovom primeru:
mallockreira memoriju za spojene stringove.strcpykopira prvi string,strcatdodaje drugi.freeoslobađa memoriju nakon korišćenja, čime se sprečava curenje memorije.
|
Prethodno
|< Dvodimenzioni dinamički nizovi-matrice |
Sledeće
Pokazivači u C jeziku >| |

