C++ 成员和成员函数的模糊部分模板专门化

C++ 成员和成员函数的模糊部分模板专门化,c++,templates,c++11,sfinae,C++,Templates,C++11,Sfinae,我不明白为什么在使用&t::b和&t::c时,由于“类模板实例化不明确”,该代码无法在main()中编译。这是g++4.6.1的一个bug吗 #include <iostream> #include <string> using namespace std; struct T{ int a; void b(){} int c() { return 1; } }; template<typename CT

我不明白为什么在使用
&t::b
&t::c
时,由于“类模板实例化不明确”,该代码无法在
main()
中编译。这是g++4.6.1的一个bug吗

#include <iostream>
#include <string>
using namespace std;

struct T{
    int a;
    void b(){}
    int c()
    { 
        return 1; 
    }
};

template<typename CT, CT> struct member_helper;

template<typename FT, FT(T::*mem)> 
struct member_helper<FT(T::*), mem> {
    static string worker()
    { 
        return "for members"; 
    }
};

template<typename Return, typename... Args, Return(T::*fun)(Args...)> 
struct member_helper<Return(T::*)(Args...), fun> {
    static string worker()
    { 
        return "for member functions returning non void"; 
    }
};

template<typename... Args, void(T::*fun)(Args...)> 
struct member_helper<void(T::*)(Args...), fun> {
    static string worker()
    { 
        return "for member functions returning void"; 
    }
};

int main() {
    cout << member_helper<decltype(&T::a), &T::a>::worker();    //prints for members, ok
    cout << member_helper<decltype(&T::b), &T::b>::worker();    //cannot distinguish between all of the three
    cout << member_helper<decltype(&T::c), &T::c>::worker();    //cannot distinguish between member function returning non void and member
}
这是copmiler版本:

使用内置规格。COLLECT\u GCC=/usr/bin/g++-4.6.real COLLECT_LTO_WRAPPER=/usr/lib/gcc/x86_64-linux-gnu/4.6.1/LTO-WRAPPER 目标:x86_64-linux-gnu配置为:../src/configure-v --使用pkgversion='Ubuntu/Linaro 4.6.1-9ubuntu3'——使用bugurl=file:///usr/share/doc/gcc-4.6/README.Bugs ——启用语言= C、C++、FORTRAN、Objc、Obj-C++,go--prefix=/usr--program suffix=-4.6--enable shared--enable linker build id--with system zlib--libexecdir=/usr/lib--include gettext--enable threads=posix--gxx include dir=/usr/c++/4.6--libdir=/usr/lib enable nls--with sysroot=/--enable clocale=gnu--enable libstdcxx debug--enable libstdcxx time=yes--启用插件——启用objc gc——禁用werror——with-arch-32=i686——with-tune=generic——启用检查=release——build=x86_64-linux-gnu——host=x86_64-linux-gnu——target=x86_64-linux-gnu线程模型:posix gcc版本4.6.1(Ubuntu/Linaro 4.6.1-9ubuntu3)


这是一个g++--它在4.8.x中为将来遇到它的人固定。

这是一个g++--它在4.8.x中为将来遇到它的人固定。

(@Nawaz:T是一个真正的类型,上面的结构-非常混乱)@Mat:有趣。他正在使用模板,并将
T
定义为类,造成混乱,尽管英文字母表有26个字母。@Griwes:使用4.5.3编译,但在4.6.2和4.7中失败。除了完整的错误消息(包括编译器认为它们不明确的原因)之外,还应该包括编译器和版本,由于这是一个非常棘手的问题,编译器可能无法正确处理它(我感觉不同的部分专门化有一个完整的顺序“returning void”比“returning non void”更专业,而“member”更专业,所以这可能是编译器的问题)我正在尝试在类主体内的typedefs中使用enable_来解决这个问题,g++4.6.1崩溃了!!但是它似乎在4.5.1中运行得很好:(@Nawaz:T是一个真正的类型,上面的结构-非常混乱)@Mat:funcy。他正在使用模板,并将
T
定义为类,造成混乱,尽管英文字母表有26个字母。@Griwes:使用4.5.3编译,但在4.6.2和4.7中失败。除了完整的错误消息(包括编译器认为它们不明确的原因)之外,还应该包括编译器和版本,由于这是一个非常棘手的问题,编译器可能无法正确处理它(我感觉不同的部分专门化有一个完整的顺序“returning void”比“returning non void”更专业,而“member”更专业,所以这可能是编译器的问题)我正在尝试在类主体内的typedefs中使用enable_来解决这个问题,g++4.6.1崩溃了!!但它似乎运行良好,符合4.5.1:
g++ -O0 -g3 -Wall -c -fmessage-length=0 -std=c++0x -MMD -MP -MF"main.d" -MT"main.d" -o "main.o" "../main.cpp" 
../main.cpp: In function ‘int main()’: 
../main.cpp:27:45: error: ambiguous class template instantiation for ‘struct member_helper’ 
../main.cpp:13:43: error: candidates are: struct member_helper 
../main.cpp:17:78: error: struct member_helper 
../main.cpp:21:59: error: struct member_helper 
../main.cpp:27:8: error: incomplete type ‘member_helper’ used in nested name specifier
../main.cpp:28:45: error: ambiguous class template instantiation for ‘struct member_helper’ 
../main.cpp:13:43: error: candidates are: struct member_helper 
../main.cpp:17:78: error: struct member_helper 
../main.cpp:28:8: error: incomplete type ‘member_helper’ used in nested name specifier make: * [main.o] Errore 1