2

我正在尝试使用具有相同功能的不同类型的不同类型的容器,但无法说服我的编译器。以下是我尝试过的一些事情:

#include <iostream>
#include <vector>
#include <list>
using namespace std;

// error: expected a qualified name after 'typename'
template<typename C<T>>
void func1() {
  C<T> c;
  c.push_back(new T);
}

// error: expected a qualified name after 'typename'
template<typename C<typename T>>
void func2() {
  C<T> c;
  c.push_back(new T);
}

// error: expected a qualified name after 'typename'
template<typename C<template <typename T>>>
void func3() {
  C<T> c;
  c.push_back(new T);
}

int main(int argc, char *argv[]) {
  func1<vector<int>>();
  func1<list<float>>();

  func2<vector<int>>();
  func2<list<float>>();

  func3<vector<int>>();
  func3<list<float>>();
  return 0;
}

这在 C++ 中可能吗?

4

4 回答 4

3

我认为最接近原始代码的方法(假设您需要两个参数,CT不仅仅是一个C<T>)如下:

#include <iostream>
#include <vector>
#include <list>
using namespace std;

template<template< class T, class A = allocator<T> > class C, typename T>
void func() {
  C<T*> c;
  c.push_back(new T);
}

int main(int argc, char *argv[]) {
  func<vector, int>();
  func<list, float>();
  return 0;
}

注意两点:

  1. 和模板有两个参数vectorlist第二个默认为allocator<T>T第一个参数在哪里)。你不能只用一个参数来定义模板;类型系统在实例化时会报错。

  2. 如果您有一个类型容器,C<T>push_back方法需要T(如vectorlist),则不能将其new T作为参数传递。我冒昧地将容器固定为C<T*>.

于 2013-08-30T21:36:48.847 回答
2

从你的电话中,我怀疑你只是想要这样的东西(我会让代码尽可能接近你所拥有的并保持它 C++03):

template<typename T>
void func1() {
    T t;
    t.push_back(typename T::value_type());
}

typename期望一个类型 - 任何类型 - 这就是它得到的vector<int>,list<float>等。另一方面,vector它本身只是一个模板,而不是它自己的类型。那是你需要template<template<...> class>语法的时候。

但是请注意,尝试像这样对容器进行分组通常是行不通的,因为并非每个容器都支持与其他容器相同的操作。如果您需要这样的接口,则必须区分序列容器、关联容器等。

于 2013-08-30T21:17:45.457 回答
2

我认为您在谈论“模板模板参数”

模板模板参数是一种类型模板参数,只允许使用模板类。该类模板可以具有任何类型的模板参数。例如:

template<template<typename T , typename ALLOCATOR> class CONTAINER>
void func2()
{
    CONTAINER<T,ALLOCATOR> container;

    container.push_back( T() );
} 

int main()
{
    func2<std::vector<bool>>();
}

当您需要提取作为模板参数传递的类模板的模板参数时,这很有用。
查看此问题以获取更多信息。

另一方面,正如克里斯在他的回答中注意到的那样,在您的情况下,传递类型参数并假设该类型具有成员 type 更容易,该成员value_type用于获取容器元素的类型。

于 2013-08-30T21:15:22.477 回答
1

首先new会返回一个指针,所以容器不会接受这个,改变那行,你也可以做以下事情:

template<typename Container, typename T >
void func1() {
  Container c;
  c.push_back(T());
}

在主要功能中:

func1<std::vector<int>, int >();
于 2013-08-30T21:16:05.150 回答