【问题标题】:Initializing scalars with braces用大括号初始化标量
【发布时间】:2013-01-09 09:40:12
【问题描述】:

在 C 和 C++ 中,可以使用大括号初始化数组和结构:

int a[] = {2, 3, 5, 7};
entry e = {"answer", 42};

但是,在a talk from 2007 中,Bjarne 提到此语法也适用于标量。我试过了:

int i = {7};

它确实有效!允许使用大括号初始化标量的基本原理是什么?

注意:我具体不是在谈论 C++11 统一初始化。这是很好的旧 C89 和 C++98。

【问题讨论】:

  • 这只是 C++ 语法的一部分。允许以这种方式初始化所有对象更加一致,并且可能会简化实现。
  • 你尝试过哪个 pre C++11 编译器?
  • @rhalbersma 没什么特别的,只是 Linux 上的当前 gcc(是的,gcc,不是 g++)。还有 Visual Studio 2012,还不支持统一初始化。所以不可能是这样的。
  • 我很确定你一定有,但只是为了确认,你用-pedantic编译了吗?也许它只是一个编译器扩展。

标签: c++ c initialization language-lawyer list-initialization


【解决方案1】:

允许使用大括号初始化标量的基本原理是什么?

int 是 POD。因此,在 int(以及所有内置类型)的情况下允许大括号初始化,因为它使初始化语法与其他 POD 一致

另外,我猜想 C++11 统一初始化语法背后的任何 基本原理 也(部分)适用于 C++03 允许的这种语法。只是 C++03 没有将其扩展为包括非 pod 类型,例如标准容器。

我可以看到这种初始化在 C++03 中很有帮助的一个地方。

template<typename T>
void f()
{
    T  obj = { size() } ; //T is POD: built-in type or pod-struct
    //code
}

现在可以用struct 实例化它,它以合适的成员开头,以及任何算术类型:

struct header
{ 
    size_t size; //it is the first member
    //...
};

f<header>(); //body becomes : header obj = { size(); }; which is fine
f<size_t>(); //body becomes : size_t obj = { size(); }; which is fine

还要注意POD,无论是结构还是内置类型,也可以统一初始化为:

header h = header(); //value-initialized
int    i = int();    //value-initialized

所以我相信一个原因是一致性!

【讨论】:

    【解决方案2】:

    没有提到基本原理,但来自2005 C++ Standard draft8.5 Initializers [dcl.init],第 14 条

    如果 T 是标量类型,则声明形式为 T x = { a }; 相当于 T x = a;

    请注意,C++ 98 标准仅允许大括号初始化器用于复制初始化 T x = { a },而不是用于直接初始化 T x { a },只有 T x(a) 有效。

    更新:另见question

    【讨论】:

      【解决方案3】:

      C++ 可能从 C 继承了这一点。在 C 中,主要原因是具有独特的初始化程序语法,特别是对于默认初始化程序。在 C 中,默认初始化程序是 {0}

      【讨论】:

        猜你喜欢
        • 2013-09-25
        • 2013-08-23
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2015-08-01
        • 2016-12-11
        • 2019-08-04
        • 1970-01-01
        相关资源
        最近更新 更多