我将函数模板特化的地址传递给常规模板函数没有问题:
template <typename T>
void f(T) {}
template <typename A, typename B>
void foo(A, B) {}
int main()
{
foo(&f<int>, &f<float>);
}
Run Code Online (Sandbox Code Playgroud)
但是,当我尝试将相同的特化传递给可变参数模板时:
template <typename T>
void f(T) {}
template <typename... A>
void bar(A...) {}
int main()
{
bar(&f<int>, &f<float>);
}
Run Code Online (Sandbox Code Playgroud)
我用GCC得到了以下编译器错误(我试过4.6.1和4.7.0):
test.cpp: In function 'int main()':
test.cpp:9:27: error: no matching function for call to 'bar(<unresolved overloaded function type>, <unresolved overloaded function type>)'
test.cpp:9:27: note: candidate is:
test.cpp:5:6: note: template<class ... A> void bar(A ...)
test.cpp:5:6: note: template argument deduction/substitution …Run Code Online (Sandbox Code Playgroud) 在下面,GCC将模板结构name与name类的模板成员函数混淆A,而Clang编译精细(实例):
template<typename T>
struct name {};
struct A
{
template<bool B>
void name() { }
};
template<bool B, typename T>
void f(T& x) { x.template name<B>(); }
Run Code Online (Sandbox Code Playgroud)
函数f显然是A在本例中使用类型的参数调用,但它可能是其他任何东西,因此f需要保留模板函数.
我不关心哪个编译器是正确的,我只需要一个解决方法因为我真的不知道除了之外的任何语法
x.template name<B>();
Run Code Online (Sandbox Code Playgroud)
调用成员函数,我看不出using声明或任何其他消除歧义的方式如何适用.
编辑是的,我现在尝试了更明确的语法
x.T::template name<B>();
Run Code Online (Sandbox Code Playgroud)
哪个有效,但真的很难看.有什么办法让简短的语法有效吗?否则,最好将两个名称中的一个更改为......
EDIT2我原来的版本f作品上一个普遍的参考T&&,这需要最丑
using X = typename std::remove_reference<T>::type;
x.X::template name<B>();
Run Code Online (Sandbox Code Playgroud)
以防万一T是一个参考...而这一切都是为了一个简单的函数调用.
有人问这个关于字符串附加的问题.它string s; s = s + 2;没有编译.人们给出了答案,说明operator+被定义为模板函数而operator+=不是,因此不应用自动向下转换(int(2)to char(2)).
原型是
template<typename _CharT, typename _Traits, typename _Alloc>
class basic_string{
basic_string&
operator+=(_CharT __c);
};
template<typename _CharT, typename _Traits, typename _Alloc>
inline basic_string<_CharT, _Traits, _Alloc>
operator+(const basic_string<_CharT, _Traits, _Alloc>& __lhs, _CharT __rhs);
Run Code Online (Sandbox Code Playgroud)
为什么编译器不能只使用这个原型并将int(2)转换为char(2)?
basic_string<char, _T, _A> operator+(const basic_string<char, _T, _A>, char);
Run Code Online (Sandbox Code Playgroud)
编译器(G ++ 6.3.0)抱怨说
[Note] deduced conflicting types for parameter '_CharT' ('char' and 'int')
Run Code Online (Sandbox Code Playgroud) 在下面,struct Y重载了X成员函数f.两个重载都是模板函数,但是要明确指定不同的参数(typename和int):
struct X
{
template <typename> static bool f() { return true; }
};
struct Y : public X
{
using X::f;
template <int> static bool f() { return false; }
};
int main()
{
std::cout << Y::f <void>() << " " << Y::f <0>() << std::endl;
}
Run Code Online (Sandbox Code Playgroud)
1 0按预期使用gcc 打印.然而,clang(3.3)抱怨说
[...] error: no matching function for call to 'f'
std::cout << Y::f <void>() << " " << Y::f …Run Code Online (Sandbox Code Playgroud) c++ overloading member-functions using-declaration template-function
我想编写一个执行某个模板化类的方法的函数,但如果该类没有它,也应该编译好.在这种情况下,它应该不会调用该函数.
struct A
{
void func() {}
};
struct B
{
};
template <typename T>
void anotherFunc(T t)
{
//do t.func() here if T implements func, just do nothing if it doesn't.
}
Run Code Online (Sandbox Code Playgroud)
这有可能吗?
我想知道这个代码有什么区别:
#include <type_traits>
#include <iostream>
template<typename T> using is_ref = std::enable_if_t<std::is_reference_v<T>, bool>;
template<typename T> using is_not_ref = std::enable_if_t<!std::is_reference_v<T>, bool>;
template<typename T, is_ref<T> = true>
void foo(T&&) {
std::cout << "ref" << std::endl;
}
template<typename T, is_not_ref<T> = true>
void foo(T&&) {
std::cout << "not ref" << std::endl;
}
int main() {
int a = 0;
foo(a);
foo(5);
}
Run Code Online (Sandbox Code Playgroud)
而这个不起作用:
#include <type_traits>
#include <iostream>
template<typename T> using is_ref = std::enable_if_t<std::is_reference_v<T>, bool>;
template<typename T> using is_not_ref = std::enable_if_t<!std::is_reference_v<T>, bool>;
template<typename T, typename …Run Code Online (Sandbox Code Playgroud) 首先,这不是一个重复的问题,因为1)这是一个链接器问题,编译器成功通过,因为我已经显式实例化了。2)这不是关于模板类,而是模板成员函数,3)我对代码结构有一些限制,所以一些现有的技巧不适用。我在这里搜索了我的标题,前几个线程(40832391、20330521、25320619、12848876、36940394)都是关于模板类,而不是模板成员函数。其他一些线程实际上正在谈论实例化失败,因此实际上是编译器问题,但我已经尝试过显式实例化并且编译已成功通过,重复一下。所以我希望你能抑制住把我的问题作为重复问题来结束的诱惑,这是我的帖子。
环境:
来源:
有两个项目:
1) DllProject,构建为 dll,包含两个源:Dll.h 和 Dll.cpp。
DLL.h:
#pragma once
#ifdef _WINDLL
#define API_TYPE __declspec(dllexport)
#else
#define API_TYPE __declspec(dllimport)
#endif
class API_TYPE AClass {
public:
template <class T> void Func(T& data);
template <class T> void CallFunc(T& data) {
Func<T>(data);
}
};
Run Code Online (Sandbox Code Playgroud)
DLL.cpp:
#include "Dll.h"
template <class T> void AClass::Func(T& data) {
data++;
}
template void AClass::Func<float>(float&); //attempt to …Run Code Online (Sandbox Code Playgroud) 从一些关于模板专业化的幻灯片:
#include <iostream>
using namespace std;
template<class X>
X& min(X& a, X& b)
{
return a > b ? b : a;
}
int& min(int& a, int & b)
{
// rewrite of the function in the case of int:
cout << "int explicit function\n";
return a > b ? b : a;
}
/*
new syntax – the more appropriate way:
template<>
int& min<int>(int& a, int& b)
{
cout << "int explicit function\n";
return a > b ? b …Run Code Online (Sandbox Code Playgroud) 我有以下模板类和模板函数,它们打算访问类的私有数据成员:
#include <iostream>
template<class T>
class MyVar
{
int x;
};
template<class T>
void printVar(const MyVar<T>& var)
{
std::cout << var.x << std::endl;
}
template<class T>
void scanVar(MyVar<T>& var)
{
std::cin >> var.x;
}
struct Foo {};
int main(void)
{
MyVar<Foo> a;
scanVar(a);
printVar(a);
return 0;
}
Run Code Online (Sandbox Code Playgroud)
为了将这两个函数声明为MyVar<T>友元函数,我在声明中尝试了以下方法template<class T> class MyVar来声明友元。它们都不起作用。我应该怎么做?
template<class T> friend void printVar(const MyVar&);
template<class T> friend void scanVar(MyVar&);
// compilation error
template<class T> friend void printVar(const MyVar<T>&);
template<class T> friend void scanVar(MyVar<T>&); …Run Code Online (Sandbox Code Playgroud) 我的程序的目的是创建一个数据列表,我可以在类层次结构中使用静态多态性时通过一组静态访问者访问该数据列表。
我通过 CRTP 利用静态多态性创建了一个类层次结构:
class VirtualBaseData {
public:
//someVirtualFunction
}
template<typename Derived>
class BaseData<Derived> {
public:
template<typename Visitor>
void accept(Visitor &v){
static_cast<Derived*>(this)->accept(v);
}
}
class DerivedBaseData1: BaseData<DerivedBaseData> {
public:
template<typename Visitor>
void accept(Visitor &v){
//Specific implementation
}
}
class DerivedBaseData2: BaseData<DerivedBaseData> {
public:
template<typename Visitor>
void accept(Visitor &v){
//Specific implementation
}
}
Run Code Online (Sandbox Code Playgroud)
我想将 DerivedBaseData 存储在一个容器中,以便稍后进行迭代和访问。
int main(){
std::vector<VirtualBaseData*> dataSet;
dataSet.push_back(new DerivedBaseData1);
dataSet.push_back(new DerivedBaseData2);
for(auto it = fifth.begin(); it != fifth.end(); ++it){
it->accept(); //Error: VirtualBaseData does not have a member function …Run Code Online (Sandbox Code Playgroud) c++ crtp static-polymorphism template-function static-visitor