I know we can do the following,
template <class CONTAINER>
void f(CONTAINER *c){}
int main(){
std::vector<int> v;
f(&v);
std::set<int> s;
f(&s);
}
Then, I want an alternative (convenient for my project), like the following,
template <class CONTAINER>
void f(CONTAINER<int> *c){} // the CONTAINER is the name of a template class
But, the compiler outputs
error: ‘CONTAINER’ is not a template
Is this possible?
You are looking for a template template parameter:
#include <set>
#include <vector>
template<template<typename> typename CONTAINER>
void f(CONTAINER<int> *){}
int main(){
std::vector<int> v;
f(&v);
std::set<int> s;
f(&s);
}
"Matching template template parameters to compatible arguments" is a C++17 feature. This won't work with C++14 because std::vector
has more than one template parameter.
You need -frelaxed-template-template-args
to compile this code with Clang, see: Template template parameter in function templates and How is P0522R0 breaking code?
An alternative way is to use template template parameters with variadic templates to avoid "Matching template template parameters to compatible arguments":
#include <set>
#include <vector>
template<class T, template<class, class...> class CONTAINER, class... Args>
void f(CONTAINER<T, Args...> *){}
int main(){
std::vector<int> v;
f(&v);
std::set<int> s;
f(&s);
}
or
#include <set>
#include <vector>
template<template<class, class...> class CONTAINER, class... Args>
void f(CONTAINER<int, Args...> *){}
int main(){
std::vector<int> v;
f(&v);
std::set<int> s;
f(&s);
}
This works with C++11.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With