简体   繁体   English

C++20 指定初始值设定项 char[]

[英]C++20 Designated Initializers char[]

C++20 introduces designated initialisers . C++20 引入了指定初始化器 I'm trying to initalise a character array inside a struct with the new syntax.我正在尝试使用新语法初始化结构内的字符数组。

Pretty simple problem, I think code may explain it best :非常简单的问题,我认为代码可以最好地解释它

struct Test
{
    unsigned v;
    char b[12];
};

int main()
{
    char str[12] = "hello"; // Works.
    char strb[12]{"hello"}; // Works.
    //
    Test testa
    {
        .v = 100u,
        .b = "hello" //Doesn't work...
    };
    Test testb
    {
        .v = 100u,
        .b = { "hello" } //Doesn't work...
    };
    Test testc
    {
        .v{ 100u },
        .b{ "hello" } //Doesn't work...
    };
    Test testd
    {
        .v{ 100u },
        .b{ "hello" } //Doesn't work...
    };
    Test teste
    {
        .v = 100u,
        .b = {} //This works.
    };
    Test testf
    {
        .v = 100u,
        .b = {'h', 'e', 'l', 'l', 'o', '\0'} //This works.
    };
    return 0;
}

I find this behaviour bazzar, the char str[12] = "hello";我发现这个行为集市, char str[12] = "hello"; line works just fine.线路工作得很好。 But the same initaliation form doesn't work in designated initialiser lists.但是相同的初始化形式在指定的初始化列表中不起作用。

Question : Why can't I initialize the char array with a string literal?问题:为什么我不能用字符串文字初始化 char 数组?

Edit编辑

I was previously using GCC.我以前使用的是 GCC。 This works with clang.这适用于 clang。 Is there a workaround for GCC and, is clang or GCC correct? GCC 是否有解决方法,clang 或 GCC 是否正确?

Designated initializers are a minor variation of aggregate initialization .指定初始化器是聚合初始化的一个小变种。 The only use of the designator names are to decide which aggregate member to initialize from the given brace-or-equal initializer.指示符名称的唯一用途是决定从给定的大括号或等号初始化程序中初始化哪个聚合成员。 The use of designated initialization changes nothing about the specific form of initialization and therefore, whether or not it is valid.指定初始化的使用不会改变初始化的具体形式,因此也不会改变它是否有效。

Given your Test object, Test{100u, "hello"} and Test{.v = 100u, .b = "hello"} are either both valid or both invalid.鉴于您的Test object, Test{100u, "hello"}Test{.v = 100u, .b = "hello"}要么都有效,要么都无效。 In both cases, Test::b is initialized in accord with [dcl.init.aggr]4.2 :在这两种情况下, Test::b都按照[dcl.init.aggr]4.2进行初始化:

Otherwise, the element is copy-initialized from the corresponding initializer-clause or is initialized with the brace-or-equal-initializer of the corresponding designated-initializer-clause.否则,该元素从相应的初始化子句复制初始化,或者使用相应的指定初始化子句的大括号或相等初始化子初始化。

Copy-initialization is the exact same process it would be if you simply initialized an array variable.复制初始化与您简单地初始化数组变量的过程完全相同。 Which is perfectly valid.这是完全有效的。

So your could should work.所以你的可能应该工作。 This is a compiler bug.这是一个编译器错误。

The GCC "workaround" is to wait for the bug to be fixed. GCC“解决方法”是等待错误修复。 Or go back to standard aggregate initialization until their compiler is fixed.或者 go 回到标准聚合初始化,直到他们的编译器被修复。

I would say you can't initialise it this way because they are not type compatible.我会说你不能以这种方式初始化它,因为它们类型不兼容。 Well, if seen on a strict level... or "pedantic" level;)好吧,如果从严格的角度来看……或“迂腐”的水平;)

A char array is not equal to a std::string even if they are closely related. char 数组不等于 std::string 即使它们密切相关。 To be type safe, the compiler disallows such assignments.为了类型安全,编译器不允许这样的赋值。
Even char array and char* are not identical , as Geeks for Geeks explain.正如 Geeks for Geeks 解释的那样,即使char 数组和 char* 也不相同

I cannot see anything nonsensical here... may be there is something I overlooked?我在这里看不到任何荒谬的东西......可能有什么我忽略了?

The spec you posted states in the "Notes" section at the bottom:您发布的规范在底部的“注释”部分中说明:

In C, character array of size one less than the size of the string literal may be initialized from a string literal;在 C 中,大小比字符串文字大小小一的字符数组可以从字符串文字初始化; the resulting array is not null-terminated.结果数组不是以空值结尾的。 This is not allowed in C++.这在 C++ 中是不允许的。

I would argue that this explains it.我认为这可以解释它。 But I agree, it is somewhat "hidden".但我同意,它有点“隐藏”。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM