指向双端队列<int>::push_back的指针

Pointer to deque<int>::push_back

#include <iostream>
#include <deque>

using namespace std;
main()
{
    typedef void (deque<int>::*func_ptr)(int);
    func_ptr fptr = &deque<int>::push_back;
}

我试图获取指向此函数的指针,但出现编译错误

error: cannot convert ‘void (std::deque<int>::*)(const value_type&) {aka void (std::deque<int>::*)(const int&)}’ to ‘func_ptr {aka void (std::deque<int>::*)(int)}’ in initialization
     func_ptr fptr = &deque<int>::push_back;

我想这样做是为了根据不同的条件得到指向不同成员函数的指针

我提到了 this link

push_back() 采用 const T & 参数,如错误消息所述:

cannot convert ‘void (std::deque::*)(const value_type&) ...

将您的类型别名更改为:

typedef void (deque<int>::*func_ptr)(const int &);

你正在尝试做的事情有一个更大的问题。允许实现向任何成员函数添加默认参数,因此 push_back() 的实际签名可能不同。它甚至可以添加具有相同名称(但签名不同)的附加功能。

我建议不要使用指向容器成员函数的指针。通常没有它会更好。

如已接受的答案所述,问题在于类型签名不同——对于 std::deque<T>push_back 仅具有接受 T const& 的重载,而没有T 直接。 typedef void (deque<int>::*func_ptr)(const int &) 是一种非常简洁和 cromulent 的写法。

我想解决一个 C++11 的方法来做到这一点 -- 类型别名。大家可能首先会疑惑 "why not use auto?" 这不可能,因为被访问的函数是一个重载函数,而 auto 不知道要访问哪个重载。因为原始问题嵌入了函数类型是 void(int) 的知识,所以语句 &deque<int>::push_back 选择了正确的重载。更简单语句的问题在于它包含了容器和所包含类型的知识。如果您想更改为 std::vector,或从 int 更改为 short,则必须创建所有新类型。使用类型别名,我们可以将所有内容模板化以避免嵌入类型知识:

using func_ptr = void(Cont::*)(typename Cont::const_reference);

我们可以像以前一样做一些简单的事情:

func_ptr<deque<int>> fptr = &deque<int>::push_back;

...或者我们可以在某处引用容器:

vector<short> container;

...在编译时查找它的类型,并存储一个指向它的 push_back 函数的指针,完全不关心容器是什么:

using container_type = decltype(container);
func_ptr<container_type> fptr2 = &container_type::push_back;