gpt4 book ai didi

c - 字符串的空终止似乎不起作用

转载 作者:太空宇宙 更新时间:2023-11-04 01:43:45 24 4
gpt4 key购买 nike

在这两个版本中:

//VERSION 1
char *c=malloc(10);
c[0]='h';
c[1]='i';
c[2]='\0';
c[3]='l';

printf("%s\n",c);

我得到了预期的结果,即正在打印 hi

现在在这一个:

//VERSION 2
char *c;
size_t siz=8;

c=malloc(sizeof(char)*(siz+1)); //char size is 1 byte on system

getline(&c,&siz,stdin);
c[siz]='\0';
printf("%s\n",c);

输入值“hello world”时,输出是“hello world”——我原以为它在读取第 9 个字节后不会打印任何内容(它是设置为 \0)。

为什么两者有区别?

发生这种情况是因为版本 2 中的指针 c 指向 stdin 并且“\0”修改在流中不起作用吗?如果是,那么为什么编译器现在发出任何警告或错误?

最佳答案

正如您自己在评论中指出的那样,getline 将检查指针和大小参数,以查看是否需要重新分配(或分配)缓冲区,以防流中的行超过给定的值缓冲区的大小(大小为 0 的 NULL 缓冲区是普通分配而不是重新分配)。发生这种情况时,指针和大小参数都会更改以匹配新缓冲区(请记住,您传入的是指向缓冲区指针和大小参数的指针,而不仅仅是参数本身,是引用而不是值)。

因此,在您的示例中,在分配大小为 9 个字符(在您的示例中为 9 字节)的缓冲区之后;您的 c 指针设置为至少有 9 个可用字节的内存,并且 siz 仍为 8。但是,在键入超过 8 个字符的行后(包括新行)像 "hello world\n",缓冲区被重新分配以适应整个字符串 "hello world\n\0",即 13 个字节,并且大小参数被更改到 13。因此,当 getline 返回时,c 指向这个新缓冲区,并且 siz 是 13。您不需要添加 null终止,因为 getline 会为您完成(假设成功)。您正在做的是将 c[13] 设置为 '\0' 幸运的是您在访问缓冲区末尾时没有触发任何异常(使字符串 "hello world\n\0\0")。

对于您正在寻找的结果,将原始大小放在一边,就像在宏中一样:

#define SIZE 8
char* c;
size_t siz = SIZE;
c = malloc(sizeof(char) * (siz +1));
getline(&c, &siz, stdin); // if you type something longer than 8 bytes including new line, it will trigger the realloc and siz will be changed
c[SIZE] = '\0'; // prematurely end the string at 8 bytes
printed("%s\n", c); // now you'll get shorter strings, noting siz will still keep the full length for you

关于c - 字符串的空终止似乎不起作用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57863905/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com