#c #malloc #valgrind #c-strings
#c #мэллок #вальгринд #c-струны
Вопрос:
Учитывая строку с некоторыми словами, разделенными пробелами (предложение, список слов и т. Д.), Приведенный ниже код динамически создает двумерный массив символов или массив строк для хранения каждого из слов, поэтому результатом является массив слов в исходной строке.
Вот код:
#includelt;stdio.hgt; #include lt;string.hgt; #include lt;stdlib.hgt; int main(void) { int var = 5; int len = 256; char words[] = "Hello there, I'm testing this."; char **wordlist; wordlist = malloc(var * sizeof(char*)); for(int i = 0; i lt; var; i ) { wordlist[i] = malloc((len 1) * sizeof(char)); } int position = 0; int j = 0; for (int i = 0; i lt; var; i ) { j = 0; while (words[position] != ' ' amp;amp; position lt; strlen(words)) { wordlist[i][j] = words[position]; position ; j ; } position ; } for (int i = 0; i lt; var; i ) { printf("%sn",wordlist[i]); } for (int i = 0; i lt; var; i ) { free(wordlist[i]); } free(wordlist); return 0; }
Вот результат выполнения кода:
Hello there, I'm testing this.
После запуска на valgrind я получаю следующее сообщение об ошибке:
==965486== Memcheck, a memory error detector ==965486== Copyright (C) 2002-2017, and GNU GPL'd, by Julian Seward et al. ==965486== Using Valgrind-3.16.0 and LibVEX; rerun with -h for copyright info ==965486== Command: testhp ==965486== ==965486== Conditional jump or move depends on uninitialised value(s) ==965486== at 0x4C38338: strlen (vg_replace_strmem.c:459) ==965486== by 0x4EB48D5: puts (in /usr/lib64/libc-2.28.so) ==965486== by 0x4007BA: main (in /home/main/testhp) ==965486== Uninitialised value was created by a heap allocation ==965486== at 0x4C34F0B: malloc (vg_replace_malloc.c:307) ==965486== by 0x4006FB: main (in /home/main/testhp) ==965486== Hello there, I'm testing this. ==965486== ==965486== HEAP SUMMARY: ==965486== in use at exit: 0 bytes in 0 blocks ==965486== total heap usage: 7 allocs, 7 frees, 2,349 bytes allocated ==965486== ==965486== All heap blocks were freed -- no leaks are possible ==965486== ==965486== For lists of detected and suppressed errors, rerun with: -s ==965486== ERROR SUMMARY: 5 errors from 1 contexts (suppressed: 0 from 0)
Почему он жалуется на «Условный переход или перемещение зависит от неинициализированных значений» и как я могу это исправить? Я думал, что правильно распределил свою память? Значение len в моем коде должно быть каким-то высоким пределом, потому что в целом мы не знаем, какой длины будет каждое слово в начальной строке или где находятся пробелы. Кроме того, хотя строки не могут быть назначены с помощью ‘=’, они могут быть назначены ‘char’ с помощью ‘char’, поэтому строка
wordlist[i][j] = words[position];
действительно, и я не вижу с этим никаких проблем. Заранее спасибо за помощь!
Комментарии:
1.
wordlist[i]
не завершается нулем. Это обычная причина «неинициализированного значения» внутри строковой функции: отсутствовал нулевой терминатор, поэтому функция считала дальше предполагаемого конца строки и начинала считывать неинициализированную память за ее пределами.