web-dev-qa-db-ja.com

= {}初期化がタプルに対して機能しないのはなぜですか?

私にとって、pairTupleの特別な場合ですが、次のことに驚いています。

pair<int, int> p1(1, 2);   // ok
Tuple<int, int> t1(1, 2);  // ok

pair<int, int> p2={1, 2};  // ok
Tuple<int, int> t2={1, 2}; // compile error

{}を使用してTupleを初期化すると、なぜ違いがあるのですか?

g++ -std=c++1yも試しましたが、まだエラーがあります。

a.cc: In function 'int main()':
a.cc:9:29: error: converting to 'std::Tuple<int, int>' from initializer list would use explicit constructor 'constexpr std::Tuple<_T1, _T2>::Tuple(_U1&&, _U2&&) [with _U1 = int; _U2 = int; <template-parameter-2-3> = void; _T1 = int; _T2 = int]'
     Tuple<int, int> t2={1, 2};
                             ^
26
Deqing

Tupleコンストラクター 呼び出そうとしているのはexplicitなので、 copy-list-initialization失敗します 。対応する pairコンストラクターexplicitではありません。

コードをに変更します

Tuple<int, int> t2{1, 2};

そしてそれはコンパイルされます。

24
Praetorian

Praetorian's正解 (私が賛成した)に加えて、もう少し情報を追加したかった...

C++ 14以降、次のことができるように標準が変更されました。

Tuple<int, int> t2={1, 2}; 

コンパイルして、期待されるセマンティクスを持たせる。これを行う提案は N4387 です。これにより、次のような構成も可能になります。

Tuple<int, int>
foo()
{
    return {1, 2};
}

T内のすべてのTupleがすべての引数から暗黙的に解釈可能である場合にのみ許可されます。

不適合な拡張機能として、libc ++はすでにこの動作を実装しています。

25
Howard Hinnant