[英]SFINAE error on VS2013?
我一直在嘗試使_CallWithRightmostArgsInner
函數正常失敗的任何事情,以便SFINAE可以正常工作,並且通過這種嘗試,VS2013給了我錯誤: error C2039: 'type' : is not a member of 'std::enable_if<false,void>'
有任何想法嗎? 有沒有更好的選擇? 這里的想法是,如果Function接受NumArgs表示的數字或參數,我想對Function進行函數調用。 最后兩個可變參數應轉發給函數,並返回結果。
template <typename Function, int NumArgs>
class SplitParameters {
public:
typedef typename function_traits<Function>::result_type result_type;
template <typename ... RightArgs>
static result_type CallWithRightmostArgs(const Function& call, RightArgs && ... rightArgs) {
static_assert(sizeof...(RightArgs) >= NumArgs, "Unable to make function call with fewer than minimum arguments.");
return _CallWithRightmostArgs(call, std::forward<RightArgs>(rightArgs)...);
}
private:
template <typename ... RightArgs>
static result_type _CallWithRightmostArgs(const Function& call, RightArgs && ... rightArgs) {
return _CallWithRightmostArgsInner(call, std::forward<RightArgs>(rightArgs)...);
}
// note the '==' vs '!=' in these two functions. I would assume that only one could exist
template <typename LeftArg, typename ... RightArgs, typename std::enable_if<sizeof...(RightArgs) != NumArgs>::type* = 0>
static result_type _CallWithRightmostArgsInner(const Function& call, LeftArg, RightArgs && ... rightArgs) {
return _CallWithRightmostArgs(call, std::forward<RightArgs>(rightArgs)...);
}
template <typename LeftArg, typename ... RightArgs, typename std::enable_if<sizeof...(RightArgs) == NumArgs>::type* = 0>
static result_type _CallWithRightmostArgsInner(const Function& call, LeftArg, RightArgs && ... rightArgs) {
return call(std::forward<RightArgs>(rightArgs)...);
}
};
我通過將代碼更改為g ++-4.8來工作
#include <iostream>
template <class T>
struct function_traits
{
typedef void result_type;
};
template <typename Function, int NumArgs>
class SplitParameters {
public:
typedef typename function_traits<Function>::result_type result_type;
template <typename ... RightArgs>
static result_type CallWithRightmostArgs(const Function& call, RightArgs && ... rightArgs) {
static_assert(sizeof...(RightArgs) >= NumArgs,
"Unable to make function call with fewer than minimum arguments.");
return _CallWithRightmostArgs(call, std::forward<RightArgs>(rightArgs)...);
}
private:
template <typename ... RightArgs>
static result_type _CallWithRightmostArgs(const Function& call, RightArgs && ... rightArgs) {
return _CallWithRightmostArgsInner(call, std::forward<RightArgs>(rightArgs)...);
}
// note the '==' vs '!=' in these two functions. I would assume that only one could exist
template <typename LeftArg, typename ... RightArgs, class = typename std::enable_if<sizeof...(RightArgs) != NumArgs -1 >::type>
static result_type _CallWithRightmostArgsInner(const Function& call, LeftArg, RightArgs && ... rightArgs) {
return _CallWithRightmostArgsInner(call, std::forward<RightArgs>(rightArgs)...);
}
template <typename ... RightArgs, class = typename std::enable_if<sizeof...(RightArgs) == NumArgs>::type>
static result_type _CallWithRightmostArgsInner(const Function& call, RightArgs && ... rightArgs) {
return call(std::forward<RightArgs>(rightArgs)...);
}
};
void f(int i, int j)
{
std::cout << i << ' ' << j << std::endl;
}
int main()
{
SplitParameters<decltype(f), 2>::CallWithRightmostArgs(f, 1, 2, 3, 4);
}
編譯器不喜歡您從_CallWithRightmostArgsInner
調用_CallWithRightmostArgs
,並且我認為您實際上是在嘗試調用Inner
函數。
g ++還不喜歡在模板參數列表中將0
轉換為void*
,因此我將其改為class = enable_if<...>::type
。
我沒有詳細研究它失敗的原因,希望這對您足夠。
編輯 :關於typename enable_if<...>::type* = 0
被拒絕,我記得std::array
有一個類似的問題:
template <class T, int size>
void f(const std::array<T,size>&){}
這個小片段可以自行編譯,但是當您這樣做時:
std::array<int,4> a;
f(a);
g++ gives:
test3.cpp: In function ‘int main()’:
test3.cpp:9:8: error: no matching function for call to ‘f(std::array<int, 4ul>&)’
f(a);
^
test3.cpp:9:8: note: candidate is:
test3.cpp:4:6: note: template<class T, int size> void f(const std::array<T, size>&)
void f(const std::array<T,size>&){}
^
test3.cpp:4:6: note: template argument deduction/substitution failed:
test3.cpp:9:8: note: mismatched types ‘int’ and ‘#‘integer_cst’ not supported by dump_type#<type error>’
f(a);
^
test3.cpp:9:8: note: ‘std::array<int, 4ul>’ is not derived from ‘const std::array<T, size>’
事實證明,問題是我將模板聲明為采用int
作為size
參數,但是編譯器得到的是std::size_t
,它與int
,即使您可以輕松地在它們之間進行轉換。
在上面的示例中,我什至無法將= 0
替換= 0
= NULL
因為這只是一個0L
文字,我必須做= (void*)0
才能使編譯器接受它(因為默認類型的enable_if<true>::type
為void
)。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.