タプルに似たものを作成しようとしていますが、私のコンストラクタの作成に問題が発生しました。ここでタプルのようなvariadicクラスのための完全なフォワーディングコンストラクタを作成する方法
コードです:
今#include <tuple>
template <typename... Ts>
struct B {
template <typename... ArgTypes>
explicit B(ArgTypes&&... args)
{
static_assert(sizeof...(Ts) == sizeof...(ArgTypes),
"Number of arguments does not match.");
}
};
struct MyType {
MyType() = delete;
MyType(int x, const char* y) {}
};
int main()
{
B <int, char> a{2, 'c'}; // works
B <int, bool, MyType, char> b{2, false, {4, "blub"}, 'c'}; // fails
std::tuple<int, bool, MyType, char> t{2, false, {4, "blub"}, 'c'}; // works
}
初期化子として単純型を渡した場合、これは[OK]を動作しますが、私は非自明なためブレースで囲まれた初期化子リストで引数を渡すしようとする場合には、しませんオブジェクト。
GCC-4.7には、以下を発する:
vararg_constr.cpp:21:67: error: no matching function for call to 'B<int, bool, MyType, char>::B(<brace-enclosed initializer list>)'
vararg_constr.cpp:21:67: note: candidates are:
vararg_constr.cpp:6:14: note: B<Ts>::B(ArgTypes&& ...) [with ArgTypes = {}; Ts = {int, bool, MyType, char}]
vararg_constr.cpp:6:14: note: candidate expects 0 arguments, 4 provided
クラン-3.1以下:
vararg_constr.cpp:21:40: error: no matching constructor for initialization of
'B<int, bool, MyType, char>'
B <int, bool, MyType, char> b{2, false,{4, "blub"}, 'c'}; // fails
^~~~~~~~~~~~~~~~~~~~~~~~~~~~
vararg_constr.cpp:6:14: note: candidate constructor not viable: requires 2
arguments, but 4 were provided
explicit B(ArgTypes&&... args)
[OK]を、今私を非常に作るもの、非常に好奇心が、それはタプルのために働くということです!標準(20.4.2.1)によれば、コンストラクタを持っていますが、これは私のようなものです。
template <class... Types>
class tuple {
public:
// ...
template <class... UTypes>
explicit tuple(UTypes&&...);
// ...
};
同じ方法でタプルオブジェクトを構築すると、機能します。
私は知りたいと思います:
A)なんで? std :: tupleはなぜ特別なのですか?また、コンパイラーが正しい引数数を推測しないのはなぜですか?
B)この作業を行うにはどうすればよいですか?
A)タプルのコンストラクタに対して、MyTypeではなくタプルであることをコンパイラがどのように認識していますか? B)申し訳ありませんが、私はタプルについて少し詳しく説明してください。 TupleはTsでパラメータ化されています...しかし、私が話しているコンストラクタは、UTypesでさらにパラメータ化されています。 –
私は問題をA)もう少し修正するように編集しました – ipc
部分Aについては、囲みテンプレートのパラメータに '&&'を付けることは、意味を変更してもはや完全な転送ではなくなりますが、 Ts)は望ましくないr値参照を形成する。パートBの場合、右辺値は左辺値「const」に「訂正」されているので、通常は機能しますが、それでも完全な転送はできません。 – Potatoswatter