getline 不将字符串存储在变量中
getline doesn't store the string in the variable
我编写了一个函数来打开用户指定名称的文件:
#include <stdio.h>
#include <stdlib.h>
void getfile(FILE** pfile)
{
void getrep(char*,char,char);
void clear(void);
char rep;
char* nfile=NULL;
printf("Name of the file: ");
clear();
nfile=NULL;
getline(&nfile,NULL,stdin);
printf("The name of the file is: %s\n",nfile);
*pfile=fopen(nfile,"r");
while(!*pfile)
{
printf("Can't open the file. Want to retry <Y/N> ? ");
getrep(&rep,'Y','N');
if(rep=='Y')
{
system("clear");
free(nfile);
nfile=NULL;
printf("Name of the file: ");
clear();
getline(&nfile,NULL,stdin);
printf("The name of the file is: %s\n",nfile);
*pfile=fopen(nfile,"r");
}
else
exit(-1);
}
free(nfile);
}
getrep 函数只是确保用户给出 Y 或 N 或 y 或 n 作为答案。这是清除函数:
#include <stdio.h>
void clear(void)
{
char c;
while((c=getchar())!=EOF && c!='\n');
}
这是我 运行 程序得到的结果:
Name of the file: Data.dat
The name of the file is: (null)
Can't open the file. Want to retry ?
当我使用调试器 gdb 并在输入文件名后打印 nfile 的值时,它仍然是 0x0,即 NULL。 (您可能已经注意到我没有为 nfile 分配内存,但我将此变量初始化为 NULL,以便 getline 为我完成它。我使用 getline 而不是 gets 因为它看起来更好,毕竟 ubuntu 16.04 讨厌得到)
我认为发生这种情况的原因是当要求用户输入名称时,这是由于 clear 函数中的 getchar() 造成的。因此,用户输入的名称被删除,nfile 在 getline 中什么也接收不到。我也尝试使用这个 clear 函数来代替:
#include <stdio.h>
void clear2(void)
{
char c;
while((c=getchar())!='\n');
}
不幸的是,我得到了同样的结果。我使用 fflush(stdin);
而不是 clear();
但这次程序跳过 getline 不让用户输入任何内容。我还删除了 file: in printf("Name of the file: ");
之后的 space 但没有任何变化。
你能帮帮我吗?提前致谢!
问题出在 getline
调用中。
传入的第二个参数NULL
不正确
应该是这样的:
size_t n = 0;
getline(&nfile,&n,stdin);
根据 getline
的 man page,声明:
ssize_t getline(char **lineptr, size_t *n, FILE *stream);
If *lineptr is set to NULL and *n is set 0 before the call, then
getline() will allocate a buffer for storing the line. This buffer
should be freed by the user program even if getline() failed.
If *lineptr
is set to NULL and *n
is set 0
before the call, then getline()
will allocate a buffer for storing the line
由于您将 NULL
指针作为 n
参数传递,调用不会为您分配缓冲区。您需要显式传递指向已初始化为零的 size_t
变量的指针:
char *nfile = NULL;
size_t n = 0;
getline(&nfile,&n,stdin);
我编写了一个函数来打开用户指定名称的文件:
#include <stdio.h>
#include <stdlib.h>
void getfile(FILE** pfile)
{
void getrep(char*,char,char);
void clear(void);
char rep;
char* nfile=NULL;
printf("Name of the file: ");
clear();
nfile=NULL;
getline(&nfile,NULL,stdin);
printf("The name of the file is: %s\n",nfile);
*pfile=fopen(nfile,"r");
while(!*pfile)
{
printf("Can't open the file. Want to retry <Y/N> ? ");
getrep(&rep,'Y','N');
if(rep=='Y')
{
system("clear");
free(nfile);
nfile=NULL;
printf("Name of the file: ");
clear();
getline(&nfile,NULL,stdin);
printf("The name of the file is: %s\n",nfile);
*pfile=fopen(nfile,"r");
}
else
exit(-1);
}
free(nfile);
}
getrep 函数只是确保用户给出 Y 或 N 或 y 或 n 作为答案。这是清除函数:
#include <stdio.h>
void clear(void)
{
char c;
while((c=getchar())!=EOF && c!='\n');
}
这是我 运行 程序得到的结果:
Name of the file: Data.dat
The name of the file is: (null)
Can't open the file. Want to retry ?
当我使用调试器 gdb 并在输入文件名后打印 nfile 的值时,它仍然是 0x0,即 NULL。 (您可能已经注意到我没有为 nfile 分配内存,但我将此变量初始化为 NULL,以便 getline 为我完成它。我使用 getline 而不是 gets 因为它看起来更好,毕竟 ubuntu 16.04 讨厌得到)
我认为发生这种情况的原因是当要求用户输入名称时,这是由于 clear 函数中的 getchar() 造成的。因此,用户输入的名称被删除,nfile 在 getline 中什么也接收不到。我也尝试使用这个 clear 函数来代替:
#include <stdio.h>
void clear2(void)
{
char c;
while((c=getchar())!='\n');
}
不幸的是,我得到了同样的结果。我使用 fflush(stdin);
而不是 clear();
但这次程序跳过 getline 不让用户输入任何内容。我还删除了 file: in printf("Name of the file: ");
之后的 space 但没有任何变化。
你能帮帮我吗?提前致谢!
问题出在 getline
调用中。
传入的第二个参数NULL
不正确
应该是这样的:
size_t n = 0;
getline(&nfile,&n,stdin);
根据 getline
的 man page,声明:
ssize_t getline(char **lineptr, size_t *n, FILE *stream);
If *lineptr is set to NULL and *n is set 0 before the call, then getline() will allocate a buffer for storing the line. This buffer should be freed by the user program even if getline() failed.
If
*lineptr
is set to NULL and*n
is set0
before the call, thengetline()
will allocate a buffer for storing the line
由于您将 NULL
指针作为 n
参数传递,调用不会为您分配缓冲区。您需要显式传递指向已初始化为零的 size_t
变量的指针:
char *nfile = NULL;
size_t n = 0;
getline(&nfile,&n,stdin);