C++ 关于弦的几个问题

C++ 关于弦的几个问题,c++,c,arrays,string,initialization,C++,C,Arrays,String,Initialization,我遇到了一个问题。在下面的代码中,我希望字符串p的长度为3,但实际长度为6。这是我想知道的第一个地方。然后,当我自己调试时,被调试的p的长度与预期结果一致。这让我感到很困惑。我不知道为什么p的长度是6,为什么调试时长度变成3。有人能回答这个问题吗 #include <cstring> #include <cstdio> int main() { char p[]={'a','b','c'}, q[10] = {'a','b','c'}; printf("

我遇到了一个问题。在下面的代码中,我希望字符串p的长度为3,但实际长度为6。这是我想知道的第一个地方。然后,当我自己调试时,被调试的p的长度与预期结果一致。这让我感到很困惑。我不知道为什么p的长度是6,为什么调试时长度变成3。有人能回答这个问题吗

#include <cstring>
#include <cstdio>

int main()
{
    char p[]={'a','b','c'}, q[10] = {'a','b','c'};
    printf("%p  %p\n",&q,&p);
    printf("%d  %d\n",strlen(q),strlen(p));
    return 0;
}
#包括
#包括
int main()
{
字符p[]={'a','b','c'},q[10]={'a','b','c'};
printf(“%p%p\n”、&q和&p);
printf(“%d%d\n”,strlen(q),strlen(p));
返回0;
}

问题是,
p
不是以null结尾的字符数组,因此不能用作字符串。将此作为参数用于预期字符串的函数调用将导致

包含UB的程序的输出不能以任何方式进行调整

为了添加更多的上下文,
q
以null结尾,根据初始值设定项列表的参数小于聚合大小的规则,其余的成员将被初始化,就像它们有静态存储一样,因此在
char
类型的情况下,它们将被初始化为
0
(这是字符串所需的null终止符)。因此,使用
q
作为字符串是可以的

解决方案:

你也可以

  • 提及比初始值设定项列表中的元素更多的维度
  • 将空值作为初始值设定项列表中的最后一个元素
    {'a'、'b'、'c'、'\0'}
  • 使用字符串(而不是初始值设定项列表)初始化数组,如
    “abc”
    ,它将在数组中包含空终止符

    • 在C语言中,字符串必须以空字节结尾,这就是strlen查找长度的方式。像这样声明字符串,长度将正确显示:

      charp[]={'a','b','c','\0'},q[10]={'a','b','c','\0'};
      
      p
      不以null结尾
      strlen
      一直计数,直到它看到空值(或者您的程序被中止,因为您访问的内存不是您的)


      请注意,
      q
      已初始化,初始值设定项中未提供的任何数组元素均设置为null。

      p
      未以null结尾
      strlen
      会一直计数,直到它看到一个空值为止(或者您的程序被中止,因为您访问的内存不是您的内存)。您正在
      p
      上使用
      strlen
      ,并且
      p
      没有履行使用
      strlen
      的合同,这会导致未定义的行为。对于未定义的行为,任何事情都可能发生。该计划可能会产生荒谬的结果。它似乎工作正常。它可能会崩溃。或任何其他无法解释的行为。请注意,
      q
      已初始化,且初始值设定项中未提供的任何数组元素均设置为null。或
      char p[]=“abc”,q[10]=“abc”
      注意,
      q
      已经是正确的-对于数组,
      {}
      初始化提供的元素的数量,其余元素初始化为零<代码>字符q[10]={'a','b','c'}中保证有
      a
      b
      c
      和7个零。谢谢。事实上,这个问题是一个考试题,我的选择是3和3。看来这个问题可能不严格好吧,我再次确认了这个问题。正确的答案提到p的长度未知,q的长度为3。@tangger是的,就这样。@tangger-事实上这个问题很严格。
      strlen(p)
      的计算给出了未定义的行为。另外,
      strlen()
      返回一个
      size\u t
      -这是一个无符号类型-因此使用
      %d
      打印它(它期望提供一个
      int
      ,如果没有传递
      int
      ,则具有未定义的行为)也会给出未定义的行为。所以3和3不是保证输出。事实上,如果您给出的答案是任何特定的输出都是预期的,那么您的答案是不正确的。在调试和发布版本之间获得不同的行为是未定义行为的典型(不保证)症状