c/c++语言开发共享在c中声明可变长度的字符串 – 显然是动态的?

我试图理解一些关于如何在c中定义“字符串”的基本知识。

char s[2]; scanf("%s", s); printf("%s", s); printf("sizeof s %d", sizeof(s)); 

我不是程序员。 我知道使用scanf获取用户输入存在问题,我甚至没有检查其返回值等。这只是为了理解声明字符串的基本内容。

鉴于上面的代码,如果我输入’helloworld’,它的作用是print’helloworld’。 好。 但我想通过说char s [2]我说的是’s是一个长度为2的数组,其中每个元素都是char’类型。

因此,我期待看到’他’打印。 不是’helloworld’。 因为我的arrays只有2个字符的空间。

sizeof仍然返回2.但看起来我的数组已经增长到用户输入的大小。

怎么了?

    两个问题:

    %s转换规范告诉printf打印从指定地址开始的字符序列 ,直到它在字符串末尾看到0终止符。 类似地,它告诉scanf存储从指定地址开始的字符序列,直到它看到空白字符或EOF。

    当您将表达式 s作为参数传递给scanfprintf ,表达式将从类型“2-element array of char ”转换为“指向char指针”,并且表达式的值是第一个元素的地址。数组(它相当于传递表达式&s[0] )。

    所有scanf接收的都是指针值 – 它不知道从该地址开始的数组有多大。 所以它不知道s只有大到足以包含两个字符。 相反,它愉快地将那些额外的字符写在数组的末尾。 类似地, printf不知道该数组只有2个字符宽 – 它只是保持打印直到它看到0终止符。

    您可以指定字段宽度作为转换的一部分:

     scanf( "%1s", s ); 

    这将从标准输入中读取最多 1个字符并将其存储到s 。 请记住, 字符串是一个字符序列,后跟一个0终结符,因此要存储一个N字符的字符串,您需要预留一个N + 1元素数组来存储它。

    这显示了为什么scanf如此危险的完美原因。 你已经覆盖了其他不适用于此的内存。 读取常量长度字符串的更安全的方法是执行类似的操作

     char a[2]; fgets(a, sizeof(a), stdin); printf("%sn", a); 

    如果你这样做并且输入了helloworld那么你只能得到hdd(因为字符串有sizeof(a) - 1由于null终止符而有sizeof(a) - 1字符。这意味着数组a实际上是{'h', ''} ) 。 读取常量大小的字符串比使用scanf更安全。

    我认为还没有人真正回答过这个问题。 这里有两个问题……

    首先,数组“s”只有2个字节长,因此任何超过1个字符的字符串的scanf都会产生不希望的结果。

     char s[255]; // was char s[2]; 

    另外,如前所述, scanf是一种输入字符串的可怕方式。 请改用fgets

     fgets(s, sizeof(s), stdin); // was scanf("%s", s); 

    其次,你不能使用sizeof来获取字符串的长度。 它会返回包含字符串的数组的长度(不是你想要的,相信我)。 相反,使用strlen

     printf("strlen s %d", strlen(s)); // was printf("sizeof s %d", sizeof(s)); 

      以上就是c/c++开发分享在c中声明可变长度的字符串 – 显然是动态的?相关内容,想了解更多C/C++开发(异常处理)及C/C++游戏开发关注计算机技术网(www.ctvol.com)!)。

      本文来自网络收集,不代表计算机技术网立场,如涉及侵权请联系管理员删除。

      ctvol管理联系方式QQ:251552304

      本文章地址:https://www.ctvol.com/c-cdevelopment/519276.html

      (0)
      上一篇 2020年12月5日
      下一篇 2020年12月5日

      精彩推荐