Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/136.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 使用模板参数时出现错误_C++_Templates_Template Templates - Fatal编程技术网

C++ 使用模板参数时出现错误

C++ 使用模板参数时出现错误,c++,templates,template-templates,C++,Templates,Template Templates,我一直在尝试创建一个模板化的classTest2,它包含两个模板参数:Type1和Type2。众所周知,第二个参数也是一个模板类,它接受2个模板参数typea和TypeB 现在,为了构造Test2的对象,我希望用户能够使用两种构造函数中的任何一种: 接受类型1和类型2的对象的人。 接受类型1、类型A和类型B的对象的人。 我编写了以下代码: #include <iostream> template<class TypeA, class TypeB> struct Test

我一直在尝试创建一个模板化的classTest2,它包含两个模板参数:Type1和Type2。众所周知,第二个参数也是一个模板类,它接受2个模板参数typea和TypeB

现在,为了构造Test2的对象,我希望用户能够使用两种构造函数中的任何一种:

接受类型1和类型2的对象的人。 接受类型1、类型A和类型B的对象的人。 我编写了以下代码:

#include <iostream>

template<class TypeA, class TypeB>
struct Test
{
    TypeA t1obj;
    TypeB t2obj;
    Test(const TypeA& t1, const TypeB& t2)
        : t1obj(t1), t2obj(t2) {std::cout<<"Test::Type1, Type2\n";}
};


template<class Type1,
         template<typename TypeX, typename TypeY> class Type2 >
struct Test2
{
    Type1 t1obj;
    Type2<typename TypeX, typename TypeY> t2obj; //Line 17

    Test2(const Type1& t1,
          const Type2<typename TypeX, typename TypeY>& t2) //Line 20
        : t1obj(t1), t2obj(t2) { std::cout<<"Test2::Type1, Type2\n";}

    Test2(const Type1& t1,
          const TypeX& x,
          const TypeY& y)
        : t1obj(t1), t2obj(x,y) { std::cout<<"Test2::Type1, X, Y\n";}

};

int main()
{
    Test<int, char> obj1(1,'a');

    Test2<int, Test<int, char> > strangeobj1(10,obj1);
    Test2<int, Test<int, char> > strangeobj2(1,2,'b');

}
我尝试了很多,但我犯了一些非常荒谬的错误,比如:


模板参数1的数量错误,在第17行和第20行应该是2。

它不是这样工作的。测试是完全成熟的类型,而不是模板。所以需要类型参数

template<class Type1,
         class Type2 >
struct Test2
{
    Type1 t1obj;
    Type2 t2obj; //Line 17

    Test2(const Type1& t1,
          const Type2& t2) //Line 20
        : t1obj(t1), t2obj(t2) { std::cout<<"Test2::Type1, Type2\n";}

    Test2(const Type1& t1,
          const typename Type2::a_type& x,
          const typename Type2::b_type& y)
        : t1obj(t1), t2obj(x,y) { std::cout<<"Test2::Type1, X, Y\n";}

};

请务必阅读,以了解为什么以及何时在使用上述类型名称之前使用typename

它不是那样工作的。测试是完全成熟的类型,而不是模板。所以需要类型参数

template<class Type1,
         class Type2 >
struct Test2
{
    Type1 t1obj;
    Type2 t2obj; //Line 17

    Test2(const Type1& t1,
          const Type2& t2) //Line 20
        : t1obj(t1), t2obj(t2) { std::cout<<"Test2::Type1, Type2\n";}

    Test2(const Type1& t1,
          const typename Type2::a_type& x,
          const typename Type2::b_type& y)
        : t1obj(t1), t2obj(x,y) { std::cout<<"Test2::Type1, X, Y\n";}

};
请务必阅读,以了解为什么以及何时在使用上述类型名称之前使用typename

Type1是一种类型,Type2是一种模板。你认为TypeX和TypeY的定义是什么?在行模板类Type2>中,它们被忽略。

Type1是类型,Type2是模板。你认为TypeX和TypeY的定义是什么?在行模板类Type2>中,它们被忽略。

这里有一个选项:

#include <iostream>

template<class TypeA, class TypeB>
struct Test
{
    TypeA t1obj;
    TypeB t2obj;
    Test(const TypeA& t1, const TypeB& t2)
        : t1obj(t1), t2obj(t2) {std::cout<<"Test::Type1, Type2\n";}
};


template<class Type1, typename TypeX, typename TypeY,
         template <typename TypeXi, typename TypeYi> class Type2>
struct Test2
{
    Type1 t1obj;
    Type2<typename TypeX, typename TypeY> t2obj; //Line 17

    Test2(const Type1& t1,
          const Type2<typename TypeX, typename TypeY>& t2) //Line 20
        : t1obj(t1), t2obj(t2) { std::cout<<"Test2::Type1, Type2\n";}

    Test2(const Type1& t1,
          const TypeX& x,
          const TypeY& y)
        : t1obj(t1), t2obj(x,y) { std::cout<<"Test2::Type1, X, Y\n";}

};

int main()
{
    Test<int, char> obj1(1,'a');

    Test2<int, int, char, Test> strangeobj1(10,obj1);
    Test2<int, int, char, Test> strangeobj2(1,2,'b');

}
这里有一个选择:

#include <iostream>

template<class TypeA, class TypeB>
struct Test
{
    TypeA t1obj;
    TypeB t2obj;
    Test(const TypeA& t1, const TypeB& t2)
        : t1obj(t1), t2obj(t2) {std::cout<<"Test::Type1, Type2\n";}
};


template<class Type1, typename TypeX, typename TypeY,
         template <typename TypeXi, typename TypeYi> class Type2>
struct Test2
{
    Type1 t1obj;
    Type2<typename TypeX, typename TypeY> t2obj; //Line 17

    Test2(const Type1& t1,
          const Type2<typename TypeX, typename TypeY>& t2) //Line 20
        : t1obj(t1), t2obj(t2) { std::cout<<"Test2::Type1, Type2\n";}

    Test2(const Type1& t1,
          const TypeX& x,
          const TypeY& y)
        : t1obj(t1), t2obj(x,y) { std::cout<<"Test2::Type1, X, Y\n";}

};

int main()
{
    Test<int, char> obj1(1,'a');

    Test2<int, int, char, Test> strangeobj1(10,obj1);
    Test2<int, int, char, Test> strangeobj2(1,2,'b');

}

这有几个错误,但主要的错误似乎是

Test2<int, Test<int, char> >
不是传递模板参数的方式。这将通过使用

Test2<int, Test>

这是因为Test是一个模板,但Test是从该模板生成的类型。

这有几个错误,但主要错误似乎是

Test2<int, Test<int, char> >
不是传递模板参数的方式。这将通过使用

Test2<int, Test>
这是因为Test是一个模板,但Test是从该模板生成的类型。

Test与模板类Type2不匹配

第一个是模板类的实例化,它不接受任何参数。第二个是接受两个参数的模板类模式。

测试与模板类Type2不匹配


第一个是模板类的实例化,它不接受任何参数。第二个是接受两个参数的模板类模式。

确保发布第一条错误消息。其余的可能都是假的。请在代码中指出它的行。@sbi:我提到的错误是我遇到的第一个错误。从您的描述中看不清楚,所以我想我应该提到它。请确保您发布了第一条错误消息。其余的可能都是假的。请在代码中指出它的行。@sbi:我提到的错误是我得到的第一个错误。这在您的描述中并不清楚,所以我想我应该提到它。但是,为什么模板参数在这里不能捕捉提供给Type2的参数呢??你能解释一下我提到的那个错误的原因吗?我想C++0x可变模板在这里会非常有用,Test2不需要知道Type2构造函数所需的任何参数。@Ben correct。我们可以编写Test2的部分专门化,它将自动推断模板参数,而不依赖固定命名的typedef来获取它们。@Saurabh这就像期望函数指针为您提供调用它的参数的值一样。这毫无意义,因为可以使用不同的参数值多次调用函数。void fvoid*pfint a{int i=a;/*由于类似的原因,这不起作用*/}。就像可以用多个参数值实例化模板一样。模板参数的声明可以等效地写成模板类Type2。内部参数名称没有任何意义。@Saurabh要拯救什么?您还没有提出最终目标。但是,为什么模板参数在这里不能捕获提供给Type2的参数呢??你能解释一下我提到的那个错误的原因吗?我想C++0x可变模板在这里会非常有用,Test2不需要知道Type2构造函数所需的任何参数。@Ben correct。我们可以编写Test2的部分专门化,它将自动推断模板参数,而不依赖固定命名的typedef来获取它们。@Saurabh这就像期望函数指针为您提供调用它的参数的值一样。这毫无意义,因为可以使用不同的参数值多次调用函数。void fvoid*pfint a{int i=a;/*由于类似的原因,这不起作用*/}。就像可以用多个参数值实例化模板一样。模板参数的声明可以等效地写成模板类Type2。内部参数名称没有任何意义。@Saurabh要拯救什么?你还没有提出一个最终目标。这是类型2,不是类型2。
TypeX和TypeY不是从属名称。也许。编译器似乎不在乎。@Ben see。它们是独立的非限定名称。这就是为什么它在语法上是无效的。请让我听听你对常见问题的看法。@Johannes:嗯,是的。无论哪种方式,它们都不是由模板参数限定的,因此typename无效@Reinderien:您的编译器不符合标准。@Johannes:FAQ看起来不错。我只能提出一个改进,说明为什么类型名称只出现一次,总是向左,远离它修改的类型,而模板出现在范围链的中间,并且可能出现多次。它是Type 2,而不是Type 2。TypeX和TypeY不是从属名称。也许。编译器似乎不在乎。@Ben see。它们是独立的非限定名称。这就是为什么它在语法上是无效的。请让我听听你对常见问题的看法。@Johannes:嗯,是的。无论哪种方式,它们都不是由模板参数限定的,因此typename无效@Reinderien:您的编译器不符合标准。@Johannes:FAQ看起来不错。我只能提出一个改进,说明为什么类型名称只出现一次,总是向左,远离它修改的类型,而模板出现在范围链的中间,并且可能出现多次。