为什么动态调整字符串会导致崩溃?
Why dynamically resizing a string causes a crash?
考虑代码:
char *word = NULL; // Pointer at buffered string.
int size = 0; // Size of buffered string.
int index = 0; // Write index.
char c; // Next character read from file.
FILE *file = fopen(fileDir, "r");
if (file)
{
while ((c = getc(file)) != EOF)
{
printf("Current index: %d, size: %d, Word: %s\n", index, size, word);
if (isValidChar(c))
{
appendChar(c, &word, &size, &index);
}
else if (word) // Any non-valid char is end of word. If (pointer) word is not null, we can process word.
{
// Processing parsed word.
size = 0; // Reset buffer size.
index = 0; // Reset buffer index.
free(word); // Free memory.
word = NULL; // Nullify word.
// Next word will be read
}
}
}
fclose(file);
/* Appends c to string, resizes string, inceremnts index. */
void appendChar(char c, char **string, int *size, int *index)
{
printf("CALL\n");
if (*size <= *index) // Resize buffer.
{
*size += 1; // Words are mostly 1-3 chars, that's why I use +1.
char *newString = realloc(*string, *size); // Reallocate memory.
printf("REALLOC\n");
if (!newString) // Out of memory?
{
printf("[ERROR] Failed to append character to buffered string.");
return;
}
*string = newString;
printf("ASSIGN\n");
}
*string[*index] = c;
printf("SET\n");
(*index)++;
printf("RET\n");
}
对于输入:
血腥
输出:
Current index: 0, size: 0, Word: <null>
CALL
REALLOC
ASSIGN
SET
RET
Current index: 1, size: 1, Word: B** // Where * means "some random char" since I am NOT saving additional '[=11=]'. I don't need to, I have my size/index.
CALL
REALLOC
ASSIGN
CRASH!!!
所以基本上 - *string[*index] = 'B' 有效,当索引是第一个字母时,它会在第二个字母处崩溃。为什么?我可能搞砸了分配或指针,我真的不知道(新手):C
谢谢!
编辑
我还想问 - 我的代码还有什么问题吗?
这个表达式不正确:
*string[*index] = c;
由于 []
的优先级高于 *
,代码试图将双指针 string
解释为指针数组。当 *index
为零时,您将获得正确的地址,因此第一次迭代纯属巧合。
您可以通过使用括号强制执行正确的运算顺序来解决此问题:
(*string)[*index] = c;
考虑代码:
char *word = NULL; // Pointer at buffered string.
int size = 0; // Size of buffered string.
int index = 0; // Write index.
char c; // Next character read from file.
FILE *file = fopen(fileDir, "r");
if (file)
{
while ((c = getc(file)) != EOF)
{
printf("Current index: %d, size: %d, Word: %s\n", index, size, word);
if (isValidChar(c))
{
appendChar(c, &word, &size, &index);
}
else if (word) // Any non-valid char is end of word. If (pointer) word is not null, we can process word.
{
// Processing parsed word.
size = 0; // Reset buffer size.
index = 0; // Reset buffer index.
free(word); // Free memory.
word = NULL; // Nullify word.
// Next word will be read
}
}
}
fclose(file);
/* Appends c to string, resizes string, inceremnts index. */
void appendChar(char c, char **string, int *size, int *index)
{
printf("CALL\n");
if (*size <= *index) // Resize buffer.
{
*size += 1; // Words are mostly 1-3 chars, that's why I use +1.
char *newString = realloc(*string, *size); // Reallocate memory.
printf("REALLOC\n");
if (!newString) // Out of memory?
{
printf("[ERROR] Failed to append character to buffered string.");
return;
}
*string = newString;
printf("ASSIGN\n");
}
*string[*index] = c;
printf("SET\n");
(*index)++;
printf("RET\n");
}
对于输入:
血腥
输出:
Current index: 0, size: 0, Word: <null>
CALL
REALLOC
ASSIGN
SET
RET
Current index: 1, size: 1, Word: B** // Where * means "some random char" since I am NOT saving additional '[=11=]'. I don't need to, I have my size/index.
CALL
REALLOC
ASSIGN
CRASH!!!
所以基本上 - *string[*index] = 'B' 有效,当索引是第一个字母时,它会在第二个字母处崩溃。为什么?我可能搞砸了分配或指针,我真的不知道(新手):C
谢谢!
编辑 我还想问 - 我的代码还有什么问题吗?
这个表达式不正确:
*string[*index] = c;
由于 []
的优先级高于 *
,代码试图将双指针 string
解释为指针数组。当 *index
为零时,您将获得正确的地址,因此第一次迭代纯属巧合。
您可以通过使用括号强制执行正确的运算顺序来解决此问题:
(*string)[*index] = c;