Uvažujeme strukturu pro řetězec z prvního bonusového úkolu.
typedef struct {
char* data;
size_t len;
} string;
(char *cstring)
string clone_from_cstring{
= {0};
string ret .len = strlen(cstring);
retif (ret.len == 0) {
.data = 0;
ret}
else {
.data = malloc(ret.len);
ret(ret.data);
assert(ret.data, cstring, ret.len);
memcpy}
return ret;
}
void string_println(string s)
{
for (int i = 0; i < s.len; i += 1)
{
("%c", s.data[i]);
printf}
("\n");
printf}
V úkolech je zakázáno používat funkcí z string.h
, s
výjimkou funkcí memcpy, memmove, memset
.
Naprogramujte následující funkci (za její korektní implementaci lze získat 2 body).
* split_string(string str, char delimiter, int *n); string
Funkce rozdělí řetězec str
na části oddělené znakem
delimiter
, ten přitom do žádné části nepatří. Funkce vrátí
takto vzniklé řetězce v nově alokovaném poli struktur
string
, každá z těchto struktur je klonem části původního
řetězce, tj. paměť pro pole .data
je nově alokována,
pointer .data
tedy neukazuje do pole str.data
.
Počet vzniklých řetězců zapíše na adresu n
.
Příklady rozdělení řetězce (delimiter
je
'-'
)
"ahoj-svete" -> "ahoj", "svete"
"ahoj--svete" -> "ahoj", "", "svete"
"-ahoj-svete" -> "", "ahoj", "svete"
"ahoj-svete-" -> "ahoj", "svete", ""
"ahoj" -> "ahoj"
Úkolem je naprogramovat string builder. To je objekt, do kterého se dá tisknout podobně jako na terminál, ale výsledný řetězec je uchováván v paměti. Uvnitř může string builder fungovat podobně jako dynamické pole: když do něj tiskneme a je potřeba řetězec zvětšit, paměť realokujeme.
Předpokládejme následující strukturu pro string builder.
typedef struct
{
char *data;
size_t capacity;
size_t len;
} string_builder;
Za úkol je imlementovat následující funkce.
void sb_allocate(string_builder *sb, size_t capacity);
Alokuje vnitřní paměť na capacity
znaků. Funkce je
použita pouze při inicializaci prázdného builderu.
void sb_destroy(string_builder *sb);
Uvolní vnitřní pamět a příslušně nastaví položky struktury.
(string_builder sb); string sb_to_string
Vrátí obsah string builderu jako nově vytvořený string
,
jeho vnitřní data jsou nově alokována.
void sb_print_int(string_builder *sb, int i);
void sb_print_cstring(string_builder *sb, char *cs);
Funkce pro tisk do string builderu.
Ukázka použití:
= {};
string_builder sb (&sb, 5);
sb_allocate(&sb, "test ");
sb_print_cstring(&sb, -3);
sb_print_int(&sb, " string builderu");
sb_print_cstring= sb_to_string(sb);
string str (str); string_println
Kód výše vytiskne řádek:
test -3 string builderu