读线功能输出奇怪的结果 [英] read line function outputs weird results

查看:61
本文介绍了读线功能输出奇怪的结果的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

以下代码应该从一个文件中读取整行直到新行

char。但它不起作用。它产生了奇怪的结果。
结果。请帮忙。我在那里检查了mallocs和

ect,但我删除它们以帮助我调试。谢谢。


#include< stdio.h>

#include< stdlib.h>

#include< string.h>


void freadl(FILE * stream,char ** string){


char next = fgetc(stream); < br $>
char * line;


line =(char *)malloc(1 * sizeof(char));


while(next!=''\ n''){


line =(char *)realloc(line,(strlen(line)+ 1)* sizeof(char) );

line [strlen(line)] = next;

next = fgetc(stream);

}


* string =(char *)malloc((strlen(line))* sizeof(char));

strcpy(* string,line);

free(line);


}


int main(int argc,char * argv []){


FILE * fp;

fp = fopen(" fread.c"," r");


char * str;

freadl(fp,& str);


printf(" str =%s,大小为%d \ n, str,strlen(str ));


int i;


for(i = 0;我< strlen(str); i ++){


char now = str [i];

printf(" chr =%c,#=%d \ n",now ,现在);


}


}

解决方案

WStoreyII写道:


以下代码应该读取整行直到新行

来自文件的字符。但它不起作用。它产生了奇怪的结果。
结果。请帮忙。我在那里检查了mallocs和

ect,但我删除它们以帮助我调试。谢谢。


#include< stdio.h>

#include< stdlib.h>

#include< string.h>


void freadl(FILE * stream,char ** string){


char next = fgetc(stream); < br $>
char * line;


line =(char *)malloc(1 * sizeof(char));



为什么哦为什么人们还在添加这些无关的演员?不仅仅是
那个,但是sizeof(char)是,买定义1.


while(next!=''\ n' '){b / b $ b line =(char *)realloc(line,(strlen(line)+ 1)* sizeof(char));



你在一个没有空终止的char数组上调用strlen。


line [strlen(line)] = next;



你在一个没有空终止的char数组上调用strlen。


next = fgetc(stream);

}


* string =(char *)malloc((strlen(line))* sizeof(char));



你在一个没有空终止的char数组上调用strlen。


-

Ian Collins。




" Ian Collins" < ia ****** @ hotmail.comschrieb im Newsbeitrag

news:53 ************** @ mid.individual.net ...


WStoreyII写道:


> line =(char *)malloc(1 * sizeof(char) );



为什么哦为什么人们还在添加这些无关的演员?不仅仅是
那个,但是sizeof(char)是,买定义1.



有几个原因:它在很多书中都有提到关于C,它是C ++要求的


我承认这两个都不是一个很好的理由(这些书是错的,C ++是

OT在这里),但至少可以理解。还有一个小问题,还有更多重要的事情要抱怨,你不觉得吗?


再见,Jojo。


WStoreyII写道:


以下代码应该读取整行直到新行

来自文件的char。但它不起作用。它产生了奇怪的结果。
结果。请帮忙。我在那里检查了mallocs和

ect,但我删除它们以帮助我调试。谢谢。


#include< stdio.h>

#include< stdlib.h>

#include< string.h>


void freadl(FILE * stream,char ** string){


char next = fgetc(stream);



fgetc()返回一个int值。这是因为,它无法在$ char $范围内表示失败,因为它可能是合法的b $ b。因此它返回一个带外值,代表

象征性地表示为EOF。所以你应该测试每次调用fgetc(),

getc(),getchar()等等:


int next;

if((next = fgetc(stream))== EOF)/ *处理错误* /


或类似的东西。


char * line;


line =(char *)malloc(1 * sizeof(char));



C中不需要强制转换。执行:

line = malloc(1 * sizeof * line);
< blockquote class =post_quotes>
while(next!=''\ n''){


line =(char *)realloc(line,(strlen( line)+ 1)* sizeof(char));



这里有多个错误。首先,如果realloc()碰巧失败,你将使用空指针

值覆盖原始缓冲区的地址,从而无法访问它。在尝试重新分配缓冲区之前,应始终备份缓冲区的地址

。其次,如上面的

,演员再次成为不必要的。


现在出现了主要的错误。你将一个无界的数组传递给

strlen()。 strlen()用于查找C字符串的长度,并且你必须为它提供一个nul终止的数组。虽然所有字符串都是数组,但是所有数组都不是字符串,即nul终止,就像在这种情况下一样。


我建议将缓冲区增加一倍二。你必须自己跟踪缓冲区的大小,大概是用size_t

的对象。


line [strlen(line)] = next;



同样的错误。你正在使用的缓冲区是*不*存储字符串。

你只是在阅读一系列字符。 strlen()是错误的

函数使用。你必须手动跟踪缓冲区长度。


next = fgetc(stream);

}

* string =(char *)malloc((strlen(line))* sizeof(char));



这里不需要不必要的分配。动态分配

对象持续存在,直到它们被释放(或)直到程序终止。

因此,您需要做的就是将指针传递给实际缓冲区

回到调用函数,同时读取行的大小

到缓冲区。


strcpy(* string,line);

free(line);


}


int main (int argc,char * argv []){


FILE * fp;

fp = fopen(" fread.c"," r" );



检查标准库函数的返回值。假设成功是要求难以发现的错误,只需前进


char * str;

freadl (fp,& str);


printf(" str =%s,大小为%d \ n",str,strlen(str));


int i;


for(i = 0; i< strlen(str); i ++){


char now = str [i];

printf(" chr =%c,#=%d \ n",now,now);


}


}



你犯的主要错误是假设你可以找到

strlen()的任何对象的长度。后者仅适用于以零字符''\ 0''终止的对象
。对于其他物体,你必须通过其他方法跟踪它们的长度。


the following code is supposed to read a whole line upto a new line
char from a file. however it does not work. it is producing weird
results. please help. I had error checking in there for mallocs and
ect, but i removed them to help me debug. thanks.

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

void freadl ( FILE *stream, char **string ) {

char next = fgetc ( stream );
char *line;

line = (char*) malloc (1*sizeof(char));

while ( next != ''\n'' ) {

line = (char*) realloc ( line, (strlen(line) + 1) * sizeof(char) );
line [strlen(line)] = next;
next = fgetc (stream );
}

*string = (char*) malloc((strlen(line))*sizeof(char));
strcpy (*string,line);
free(line);

}

int main ( int argc, char *argv[] ) {

FILE *fp;
fp = fopen ( "fread.c", "r" );

char *str;
freadl ( fp , &str );

printf ( "str = %s, with size of %d\n", str, strlen (str) );

int i;

for ( i = 0; i < strlen (str); i++ ){

char now = str[i];
printf ( "chr = %c, # = %d\n", now,now);

}

}

解决方案

WStoreyII wrote:

the following code is supposed to read a whole line upto a new line
char from a file. however it does not work. it is producing weird
results. please help. I had error checking in there for mallocs and
ect, but i removed them to help me debug. thanks.

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

void freadl ( FILE *stream, char **string ) {

char next = fgetc ( stream );
char *line;

line = (char*) malloc (1*sizeof(char));

Why oh why are people still adding these extraneous casts? Not only
that, but sizeof(char) is, buy definition 1.

while ( next != ''\n'' ) {

line = (char*) realloc ( line, (strlen(line) + 1) * sizeof(char) );

You are calling strlen on an array of char that isn''t null terminated.

line [strlen(line)] = next;

You are calling strlen on an array of char that isn''t null terminated.

next = fgetc (stream );
}

*string = (char*) malloc((strlen(line))*sizeof(char));

You are calling strlen on an array of char that isn''t null terminated.

--
Ian Collins.



"Ian Collins" <ia******@hotmail.comschrieb im Newsbeitrag
news:53**************@mid.individual.net...

WStoreyII wrote:

>line = (char*) malloc (1*sizeof(char));

Why oh why are people still adding these extraneous casts? Not only
that, but sizeof(char) is, buy definition 1.

For several reasons: it is mentiond in lots of books about C and it is
required by C++
I admit that neither is a good reason (the books are just wrong and C++ is
OT here), but at least understandable. And a minor issue, there are more
important things to moan about, won''t you think?

Bye, Jojo.


WStoreyII wrote:

the following code is supposed to read a whole line upto a new line
char from a file. however it does not work. it is producing weird
results. please help. I had error checking in there for mallocs and
ect, but i removed them to help me debug. thanks.

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

void freadl ( FILE *stream, char **string ) {

char next = fgetc ( stream );

fgetc() returns an int value. This is because, it has no way of
indicating failure within the range of a char value, since it could be
a legal. Hence it returns an out-of-band value, represented
symbolically as EOF. So you should test each invocation of fgetc(),
getc(), getchar() etc. like:

int next;
if((next = fgetc(stream)) == EOF) /* handle error */

or something similar.

char *line;

line = (char*) malloc (1*sizeof(char));

The casts are not needed in C. Do:
line = malloc(1 * sizeof *line);

while ( next != ''\n'' ) {

line = (char*) realloc ( line, (strlen(line) + 1) * sizeof(char) );

There''re multiple error here. First, if realloc() happens to fail, you
overwrite the address of the original buffer with a null pointer
value, thus loosing access to it. You should always backup the address
of the buffer before attempting to reallocating it. Secondly, as
above, the cast is once again uneccessary.

Now coming to the main mistake. You''re passing a unbounded array to
strlen(). strlen() is used to find the length of C strings and you
must supply it a nul terminated array. While all strings are arrays,
all arrays are not strings, i.e. nul terminated, as in this case.

I suggest increasing the buffer by a factor of two. You must keep
track of the size of the buffer yourself, presumably with a size_t
object.

line [strlen(line)] = next;

Same mistake. The buffer you''re using is *not* storing a string.
You''re just reading a sequence of characters. strlen() is the wrong
function to use. You have to keep track of the buffer length manually.

next = fgetc (stream );
}

*string = (char*) malloc((strlen(line))*sizeof(char));

No need for an unneccessary allocation here. Dynamically allocated
objects persist until they''re free()''ed or until program termination.
Hence, all you need to do is to pass a pointer to the actual buffer
back to the calling function, along with the size of the line read
into the buffer.

strcpy (*string,line);
free(line);

}

int main ( int argc, char *argv[] ) {

FILE *fp;
fp = fopen ( "fread.c", "r" );

Check the return values of standard library functions. Just going
ahead assuming success is asking for difficult to find bugs.

char *str;
freadl ( fp , &str );

printf ( "str = %s, with size of %d\n", str, strlen (str) );

int i;

for ( i = 0; i < strlen (str); i++ ){

char now = str[i];
printf ( "chr = %c, # = %d\n", now,now);

}

}

The main mistake you''re making is assuming that you can find out the
length of any object with strlen(). The latter only works on objects
terminated by a nul character, ''\0''. For other objects, you''ll have to
track their length by other methods.


这篇关于读线功能输出奇怪的结果的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆