使用gdb--仍然找不到malloc错误
Using gdb--still can't find malloc error
我已经查看了之前的 posts,但它们没有帮助我找到我的问题...为了简短起见,我正在制作一个函数,应该逐行读取文本文件(是的,我知道有很多这样的 post)。但是当我通过 CMD 运行 我的程序时,它给了我这个错误:
Program received signal SIGSEGV, Segmentation fault.
__GI___libc_realloc (oldmem=0x10011, bytes=1) at malloc.c:2999
2999 malloc.c: No such file or directory.
我漂亮确定我正确地写出了我的malloc/realloc行。我已经尝试找到很多与此类似的 post,但所提供的解决方案中有 none 有帮助。如果您有任何我错过的 post 建议,请告诉我。无论如何,这是我的功能:
char* read_single_line(FILE* fp){
char* line = NULL;
int num_chars = 0;
char c;
fscanf(fp, "%c", &c);
while(!feof(fp)) {
num_chars++;
line = (char*) realloc(line, num_chars * sizeof(char));
line[num_chars -1] = c;
if (c == '\n') {
break;
}
fscanf(fp, "%c", &c);
}
if(line != NULL) {
line = realloc(line, (num_chars+1) * sizeof(char));
line[num_chars] = '[=11=]';
}
return line;
}
void read_lines(FILE* fp, char*** lines, int* num_lines) {
int i = 0;
int num_lines_in_file = 0;
char line[1000];
if (fp == NULL) {
*lines = NULL;
*num_lines = 0;
} else {
(*lines) = (char**)malloc(1 * sizeof(char*));
while (read_single_line(fp) != NULL) {
(*lines)[i] = (char*)realloc((*lines)[i], sizeof(char));
num_lines_in_file++;
i++;
}
*lines[i] = line;
*num_lines = num_lines_in_file;
}
}
非常感谢任何帮助——我是 C 语言的初学者,请听我说完!!
char line[1000];
:
while (read_single_line(fp) != NULL) {
:
}
*lines[i] = line;
这对我来说一点都不合适。你的 read_single_line
函数 return 是一个实际的行,但是除了根据 NULL
检查它之外,你实际上从未 存储 它在任何地方。相反,您将行指针指向 line
,一个自动作用域的变量,它实际上可以包含任何内容(更令人担忧的是,可能没有终止符)。
我认为您可能应该存储 read_single_line
中的 return 值并使用它来设置行指针。
顺便说一句,一次扩展一个字符的缓冲区也可能效率很低。我建议最初分配更多字节,然后保留该容量和当前正在使用的字节。然后,只有当你即将使用超出你的能力时,你才会扩展,并且扩展不止一个。在伪代码中,类似于:
def getLine:
# Initial allocation with error check.
capacity = 64
inUse = 0
buffer = allocate(capacity)
if buffer == null:
return null
# Process each character made available somehow.
while ch = getNextChar:
# Expand buffer if needed, always have room for terminator.
if inUse + 1 == capacity:
capacity += 64
newBuff = realloc buffer with capacity
# Failure means we have to release old buffer.
if newBuff == null:
free buffer
return null
# Store character in buffer, we have enough room.
buffer[inUse++] = ch
# Store terminator, we'll always have room.
buffer[inUse] = '[=11=]';
return buffer
您会注意到,除了更有效的重新分配之外,对所述分配的错误检查也更好。
while (read_single_line(fp) != NULL) {
(*lines)[i] = (char*)realloc((*lines)[i], sizeof(char));
num_lines_in_file++;
i++;
}
*lines[i] = line;
这个短片段中的错误多于行。让我们一一回顾。
while (read_single_line(fp) != NULL)
你读了一行,检查它是否是一个空指针,然后把它扔掉,而不是把它留在周围,把它累积在 lines
数组中。
(*lines)[i] = (char*)realloc((*lines)[i], sizeof(char));
您正在尝试重新分配 (*lines[i])
。首先,它不存在于 i==0
之外,因为 (*lines)
只被分配来包含一个元素。其次,重新分配单独的行是没有意义的,因为您正在(应该)从行读取功能中获得完美的现成行。你想重新分配 *lines
而不是:
*lines = realloc (*lines, i * sizeof(char*));
现在这两行
num_lines_in_file++;
i++;
本身不是错误,但为什么有两个变量总是具有完全相同的值?此外,您希望它们(它)位于 realloc 行之前,按照通常的 increment-realloc-assign 模式(您在其他函数中使用它)。
说到分配部分,没有。您现在应该插入一个:
(*lines)[i-1] = // what?
你在调用read_single_line时应该保存的行指针,就是这样。从头开始:
char* cur_line;
int i = 0;
*lines = NULL;
while ((cur_line=read_single_line(fp)) != NULL)
{
++i;
*lines = realloc (*lines, i * sizeof(char*));
(*lines)[i-1] = cur_line;
}
*num_lines = i;
最后一个
*lines[i] = line;
简直丑爆了。
首先,lines
不是一个数组,它是一个指向单个变量的指针,所以lines[i]
访问星际尘埃。其次,您正试图为其分配一个局部变量的地址,一旦您的函数 returns,该变量将不复存在。第三,它在循环外做了什么?如果你想用空指针终止你的线数组,这样做:
}
*num_lines = i;
++i;
*lines = realloc (*lines, i * sizeof(char*));
(*lines)[i-1] = NULL;
但考虑到您 return 的行数,这可能没有必要。
免责声明:none 以上内容已经过测试。如果有任何错误,请修复它们!
我已经查看了之前的 posts,但它们没有帮助我找到我的问题...为了简短起见,我正在制作一个函数,应该逐行读取文本文件(是的,我知道有很多这样的 post)。但是当我通过 CMD 运行 我的程序时,它给了我这个错误:
Program received signal SIGSEGV, Segmentation fault.
__GI___libc_realloc (oldmem=0x10011, bytes=1) at malloc.c:2999
2999 malloc.c: No such file or directory.
我漂亮确定我正确地写出了我的malloc/realloc行。我已经尝试找到很多与此类似的 post,但所提供的解决方案中有 none 有帮助。如果您有任何我错过的 post 建议,请告诉我。无论如何,这是我的功能:
char* read_single_line(FILE* fp){
char* line = NULL;
int num_chars = 0;
char c;
fscanf(fp, "%c", &c);
while(!feof(fp)) {
num_chars++;
line = (char*) realloc(line, num_chars * sizeof(char));
line[num_chars -1] = c;
if (c == '\n') {
break;
}
fscanf(fp, "%c", &c);
}
if(line != NULL) {
line = realloc(line, (num_chars+1) * sizeof(char));
line[num_chars] = '[=11=]';
}
return line;
}
void read_lines(FILE* fp, char*** lines, int* num_lines) {
int i = 0;
int num_lines_in_file = 0;
char line[1000];
if (fp == NULL) {
*lines = NULL;
*num_lines = 0;
} else {
(*lines) = (char**)malloc(1 * sizeof(char*));
while (read_single_line(fp) != NULL) {
(*lines)[i] = (char*)realloc((*lines)[i], sizeof(char));
num_lines_in_file++;
i++;
}
*lines[i] = line;
*num_lines = num_lines_in_file;
}
}
非常感谢任何帮助——我是 C 语言的初学者,请听我说完!!
char line[1000];
:
while (read_single_line(fp) != NULL) {
:
}
*lines[i] = line;
这对我来说一点都不合适。你的 read_single_line
函数 return 是一个实际的行,但是除了根据 NULL
检查它之外,你实际上从未 存储 它在任何地方。相反,您将行指针指向 line
,一个自动作用域的变量,它实际上可以包含任何内容(更令人担忧的是,可能没有终止符)。
我认为您可能应该存储 read_single_line
中的 return 值并使用它来设置行指针。
顺便说一句,一次扩展一个字符的缓冲区也可能效率很低。我建议最初分配更多字节,然后保留该容量和当前正在使用的字节。然后,只有当你即将使用超出你的能力时,你才会扩展,并且扩展不止一个。在伪代码中,类似于:
def getLine:
# Initial allocation with error check.
capacity = 64
inUse = 0
buffer = allocate(capacity)
if buffer == null:
return null
# Process each character made available somehow.
while ch = getNextChar:
# Expand buffer if needed, always have room for terminator.
if inUse + 1 == capacity:
capacity += 64
newBuff = realloc buffer with capacity
# Failure means we have to release old buffer.
if newBuff == null:
free buffer
return null
# Store character in buffer, we have enough room.
buffer[inUse++] = ch
# Store terminator, we'll always have room.
buffer[inUse] = '[=11=]';
return buffer
您会注意到,除了更有效的重新分配之外,对所述分配的错误检查也更好。
while (read_single_line(fp) != NULL) {
(*lines)[i] = (char*)realloc((*lines)[i], sizeof(char));
num_lines_in_file++;
i++;
}
*lines[i] = line;
这个短片段中的错误多于行。让我们一一回顾。
while (read_single_line(fp) != NULL)
你读了一行,检查它是否是一个空指针,然后把它扔掉,而不是把它留在周围,把它累积在 lines
数组中。
(*lines)[i] = (char*)realloc((*lines)[i], sizeof(char));
您正在尝试重新分配 (*lines[i])
。首先,它不存在于 i==0
之外,因为 (*lines)
只被分配来包含一个元素。其次,重新分配单独的行是没有意义的,因为您正在(应该)从行读取功能中获得完美的现成行。你想重新分配 *lines
而不是:
*lines = realloc (*lines, i * sizeof(char*));
现在这两行
num_lines_in_file++;
i++;
本身不是错误,但为什么有两个变量总是具有完全相同的值?此外,您希望它们(它)位于 realloc 行之前,按照通常的 increment-realloc-assign 模式(您在其他函数中使用它)。
说到分配部分,没有。您现在应该插入一个:
(*lines)[i-1] = // what?
你在调用read_single_line时应该保存的行指针,就是这样。从头开始:
char* cur_line;
int i = 0;
*lines = NULL;
while ((cur_line=read_single_line(fp)) != NULL)
{
++i;
*lines = realloc (*lines, i * sizeof(char*));
(*lines)[i-1] = cur_line;
}
*num_lines = i;
最后一个
*lines[i] = line;
简直丑爆了。
首先,lines
不是一个数组,它是一个指向单个变量的指针,所以lines[i]
访问星际尘埃。其次,您正试图为其分配一个局部变量的地址,一旦您的函数 returns,该变量将不复存在。第三,它在循环外做了什么?如果你想用空指针终止你的线数组,这样做:
}
*num_lines = i;
++i;
*lines = realloc (*lines, i * sizeof(char*));
(*lines)[i-1] = NULL;
但考虑到您 return 的行数,这可能没有必要。
免责声明:none 以上内容已经过测试。如果有任何错误,请修复它们!