2011-07-01 34 views
18

我目前正試圖理解C++ 0x的新統一初始化。不幸的是,我弄亂了使用統一的引用初始化。例如:引用的統一初始化

int main() { 
    int a; 
    int &ref{a}; 
} 

這個例子正常工作:

% LANG=C g++ uniform_init_of_ref.cpp -std=c++0x -o uni -Wall -Wextra 
uniform_init_of_ref.cpp: In function `int main()': 
uniform_init_of_ref.cpp:3:10: warning: unused variable `ref' [-Wunused-variable] 

更新科莫拋出一個錯誤爲例子,所以也許GCC不應該編譯它)

現在,如果我使用自定義數據類型而不是整數,它不再有效:

class Y 
{}; 

int main() 
{ 
    Y y; 
    Y &ref{y}; 
} 

% LANG=C g++ initialization.cpp -std=c++0x -o initialization -Wall -Wextra 
initialization.cpp: In function `int main()': 
initialization.cpp:9:13: error: invalid initialization of non-const reference of type `Y&' from an rvalue of type `<brace-enclosed initializer list>' 
initialization.cpp:9:8: warning: unused variable `ref' [-Wunused-variable] 

不幸的是,我沒有在標準草案中找到相關部分。我的猜測是,我誤解統一初始化的使用情況,科莫抱怨此消息:

ComeauTest.c(9): error: reference variable "ref" requires an initializer 
     Y &ref{y}; 

因此,可你有人點我在正確的方向?


如果你想知道爲什麼這個問題是相關的,爲什麼我不只是用Y &ref(y):我希望能夠在構造函數初始化列表中使用統一的初始化:

class X { }; 

class Y { 
    const X& x; 

    public: 
     Y (const X& xx): 
      x{xx} 
     {} 
}; 

int main() { 
    X x; 
    Y y{x}; 
} 

這會失敗,並顯示與上面相同的錯誤消息。

注:

  • 我使用LANG=C,使英語的錯誤消息。
  • gcc版本:4.6.1
+0

gcc 4.4.1沒有編譯第一個例子:'uniform_init_of_ref.cpp:3:錯誤:ISO C++禁止使用初始化列表來初始化引用 ce'ref'' – rmflow

+2

@rmflow:gcc4.4沒有完全實現統一初始化。 –

+0

您可以使用普通的'X(XX)'在構造函數初始化列表,就我看不出有什麼需要一種新奇的東西統一:-) –

回答

6

根據N2672段落8.5.4.4應該說:

Otherwise, if T is a reference type, an rvalue temporary of the type referenced by T is list-initialized, and the reference is bound to that temporary. [ Note: As usual, the binding will fail and the program is ill-formed if the reference type is an lvalue reference to a non-const type. ]

它(如果我理解正確的話)是指引用的統一初始化它們綁定到新匿名實例,所以在我看來這是非常無用的。這仍然不能解釋爲什麼一個人工作,另一個不工作;他們應該表現相同(除非Y有一些明確的構造函數)。

+0

所以在第一個例子中,執行'ref = 42'將不**修改'a'。 –

+0

@在第一個例子中,分配給'ref'的alexandre-c在這裏改變'a'的值。 – evnu

+0

@evnu:此行爲不符合@Jan引號的內容。你跟Comeau覈對過嗎? –