C - realloc 导致崩溃
C - realloc causes crash
我正在尝试实现一个从控制台读取的动态字符串数组(可以是任意长度)。但是它在循环中调用 realloc() 时崩溃。代码:
void kill(char **memory, int count) {
if (memory != NULL) {
for (int i = 0; i < count; i++) {
if (memory[i] != NULL) {
free(memory[i]);
}
}
free(memory);
}
}
char **getData(int *strCount, int *allocatedCount) {
int maxStrCount = 10;
int maxStrLength = 10;
char **data = malloc(sizeof(char *) * maxStrCount);
if (data == NULL) {
return NULL;
}
for (int i = 0; i < maxStrCount; i++) {
data[i] = malloc(sizeof(char) * maxStrLength);
if (data[i] == NULL) {
kill(data, i);
return NULL;
}
}
int i = 0;
int j = 0;
for (char ch = getchar(); ch != EOF; ch = getchar()) {
if (ch == '\n') { // if end of line
data[i][j] = '[=10=]';
i++;
j = 0;
if (i >= maxStrCount) {
// extend array
char **newData = realloc(data, sizeof(char *) * (maxStrCount * 2));
if (newData == NULL) {
kill(data, maxStrCount);
return NULL;
}
maxStrCount *= 2;
data = newData;
for (int k = i; k < maxStrCount; k++) {
data[k] = malloc(sizeof(char) * maxStrLength);
if (data[k] == NULL) {
kill(data, k);
return NULL;
}
}
}
} else { // if not end of line
data[i][j] = ch;
j++;
if (j >= maxStrLength - 1) { // extend string
maxStrLength *= 2;
char *newStr = realloc(data[i], sizeof(char) * maxStrLength); // Here it crashes
if (newStr == NULL) {
kill(data, maxStrCount);
return NULL;
}
data[i] = newStr;
}
}
}
if (j > 0) { // in case of file doesn't end with empty line
data[i][j] = '[=10=]';
i++;
}
if (i == 0) { // in case of empty input
kill(data, maxStrCount);
return NULL;
}
*strCount = i;
*allocatedCount = maxStrCount;
return data;
}
崩溃出现在以下输入上:
Lorem ipsum dolor sit
amet, consectetur
adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua
是这样的:读取"Lorem ips",然后调用realloc,然后读取"Lorem ipsum dolor s",然后再次调用realloc,一切正常。然后它读取 "amet, consectetur"(第 2 行)和 "adipiscing elit, sed do eiusmod tempor "(第 3 行),然后尝试重新分配并崩溃。
我看了这一切试图调试,但我仍然不知道它为什么会崩溃。
您正在所有字符串之间共享变量 maxStrLength
。
您正在为第 2 行重新分配缓冲区并增加缓冲区 maxStrLength
;但是,当您读取下一行时,它的缓冲区较小,因此您在此处越界写入:
data[i][j] = ch;
我正在尝试实现一个从控制台读取的动态字符串数组(可以是任意长度)。但是它在循环中调用 realloc() 时崩溃。代码:
void kill(char **memory, int count) {
if (memory != NULL) {
for (int i = 0; i < count; i++) {
if (memory[i] != NULL) {
free(memory[i]);
}
}
free(memory);
}
}
char **getData(int *strCount, int *allocatedCount) {
int maxStrCount = 10;
int maxStrLength = 10;
char **data = malloc(sizeof(char *) * maxStrCount);
if (data == NULL) {
return NULL;
}
for (int i = 0; i < maxStrCount; i++) {
data[i] = malloc(sizeof(char) * maxStrLength);
if (data[i] == NULL) {
kill(data, i);
return NULL;
}
}
int i = 0;
int j = 0;
for (char ch = getchar(); ch != EOF; ch = getchar()) {
if (ch == '\n') { // if end of line
data[i][j] = '[=10=]';
i++;
j = 0;
if (i >= maxStrCount) {
// extend array
char **newData = realloc(data, sizeof(char *) * (maxStrCount * 2));
if (newData == NULL) {
kill(data, maxStrCount);
return NULL;
}
maxStrCount *= 2;
data = newData;
for (int k = i; k < maxStrCount; k++) {
data[k] = malloc(sizeof(char) * maxStrLength);
if (data[k] == NULL) {
kill(data, k);
return NULL;
}
}
}
} else { // if not end of line
data[i][j] = ch;
j++;
if (j >= maxStrLength - 1) { // extend string
maxStrLength *= 2;
char *newStr = realloc(data[i], sizeof(char) * maxStrLength); // Here it crashes
if (newStr == NULL) {
kill(data, maxStrCount);
return NULL;
}
data[i] = newStr;
}
}
}
if (j > 0) { // in case of file doesn't end with empty line
data[i][j] = '[=10=]';
i++;
}
if (i == 0) { // in case of empty input
kill(data, maxStrCount);
return NULL;
}
*strCount = i;
*allocatedCount = maxStrCount;
return data;
}
崩溃出现在以下输入上:
Lorem ipsum dolor sit
amet, consectetur
adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua
是这样的:读取"Lorem ips",然后调用realloc,然后读取"Lorem ipsum dolor s",然后再次调用realloc,一切正常。然后它读取 "amet, consectetur"(第 2 行)和 "adipiscing elit, sed do eiusmod tempor "(第 3 行),然后尝试重新分配并崩溃。
我看了这一切试图调试,但我仍然不知道它为什么会崩溃。
您正在所有字符串之间共享变量 maxStrLength
。
您正在为第 2 行重新分配缓冲区并增加缓冲区 maxStrLength
;但是,当您读取下一行时,它的缓冲区较小,因此您在此处越界写入:
data[i][j] = ch;