昨天一个朋友问我,array为什么可以这样写
         boost::array<int,4> a = { 1, 2, 3, 4 }; 
  
     答: 重载了赋值操作符,通过类的缺省构造给赋值操作一个右值来初始化一个array变量。 至于为什么要这样做,而不直接初始化?这是为了语法形式上能够与原生数组相符合。我自以为如此就回答了这个问题 。
     朋友突然再问了一句,为什么可以这样缺省构造 ? 为什么可以 = { 1, 2, 3, 4 }; 
     是啊! 为什么!  
     那一时我就象短路了一般,是啊,为什么,为什么我不记得!  过了自己好一会才缓过气,想起了答案。下面一起看一看这个问题

     先看一看问题的代码,不论其它,只讨论初始化,boost::array代码被简化为:

     template<class T, std::size_t N> class array 
     
{
          
public:
            T elems[N];    
// fixed-size array of elements of type T
          public:
              
// assignment with type conversion
            template <typename T2>
            array
<T,N>& operator= (const array<T2,N>& rhs) 
            
{
                std::copy(rhs.begin(),rhs.end(), begin());
                
return *this;
            }

     }


     那为什么 { 1, 2, 3, 4 } 可以缺省构造出一个 boost::array 呢,是由C++ 标准的哪个条款来完成的? 
  
     其实boost::array 的 Design Rationale 中有提到了这个问题。只是这个细节平时难得用到,也就从记忆里淡出了,吓了自己好大一跳。作者将boost::array实现为一个 "aggregate" (C++标准 8.5.1节 )。这意味着可以用下面的形式完成初始化。 
     boost::array<int,4> a = { { 1, 2, 3, 4 } };
 而一个符合标准(8.5.1.11)的编译器也可以使用更少一些的大括号来完成初始化工作 
     boost::array<int,4> a = { 1, 2, 3, 4 };
  具体的标准条款摘取了三条 copy 在下面,大家可以参考。本来想翻译一下,但最终一想还是算了,英文水平有限,藏拙的好 :-)

INTERNATIONAL STANDARD
ISO/IEC 14882
Second edition
2003-10-15
Programming languages — C++

8.5.1 Aggregates
    1 An aggregate is an array or a class (clause 9) with no user-declared constructors (12.1), no private or protected
non-static data members (clause 11), no base classes (clause 10), and no virtual functions (10.3).
    2 When an aggregate is initialized the initializer can contain an initializer-clause consisting of a braceenclosed,
comma-separated list of initializer-clauses for the members of the aggregate, written in increasing
subscript or member order. If the aggregate contains subaggregates, this rule applies recursively to the members of the subaggregate. [Example:
struct A {
    int x;
    struct B {
        int i;
        int j;
    } b;
} a = { 1, { 2, 3 } };
initializes a.x with 1, a.b.i with 2, a.b.j with 3. ]

    11 Braces can be elided in an initializer-list as follows. If the initializer-list begins with a left brace, then the
succeeding comma-separated list of initializers initializes the members of a subaggregate; it is erroneous
for there to be more initializers than members. If, however, the initializer-list for a subaggregate does not
begin with a left brace, then only enough initializers from the list are taken to initialize the members of the
subaggregate; any remaining initializers are left to initialize the next member of the aggregate of which the
current subaggregate is a member. [Example:
float y[4][3] = { 
    { 1, 3, 5 }, 
    { 2, 4, 6 }, 
    { 3, 5, 7 },
};
is a completely-braced initialization: 1, 3, and 5 initialize the first row of the array y[0], namely
y[0][0], y[0][1], and y[0][2]. Likewise the next two lines initialize y[1] and y[2]. The initializer
ends early and therefore y[3]’s elements are initialized as if explicitly initialized with an expression
of the form float(), that is, are initialized with 0.0. In the following example, braces in the initializerlist
are elided; however the initializer-list has the same effect as the completely-braced initializer-list of the
above example,
float y[4][3] = { 
    1, 3, 5, 2, 4, 6, 3, 5, 7
};
The initializer for y begins with a left brace, but the one for y[0] does not, therefore three elements from
the list are used. Likewise the next three are taken successively for y[1] and y[2]. —end example]