神经网络项目中,如何在结构体中存储类非静态成员函数指针?
解决C++类成员函数指针存储问题
你遇到的核心问题是普通函数指针无法直接存储类的非静态成员函数地址——非静态成员函数隐含一个this指针参数,它的指针类型和普通函数指针完全不同,不能直接赋值。下面给两种可行的解决方案:
方案一:使用类成员函数指针
首先修改结构体,同时存储神经元实例指针和成员函数指针:
#include <iostream> #include <vector> struct previous_neuron_struct { double weight; neuron* neuron_ptr; // 存储对应的神经元实例指针 double (neuron::*return_func)(); // 成员函数指针,类型为neuron类的无参返回double的函数 }; class neuron { public: double value; std::vector<previous_neuron_struct> previous_neurons_vector; double Return_Value() { return value; } }; int main() { neuron neuron1; neuron neuron2; neuron2.value = 3.14; // 给神经元2设置值,方便测试 previous_neuron_struct* temp = new previous_neuron_struct; temp->weight = 0.5; temp->neuron_ptr = &neuron2; temp->return_func = &neuron::Return_Value; // 正确获取成员函数地址的方式 // 调用示例:必须结合实例指针调用成员函数指针 double result = (temp->neuron_ptr->*(temp->return_func))(); std::cout << "调用结果:" << result << std::endl; delete temp; return 0; }
注意点:
- 成员函数指针的声明格式必须严格匹配:
返回值类型 (类名::*指针名)(参数列表) - 获取成员函数地址必须用
&类名::成员函数名,不能通过对象实例获取 - 调用时必须用
(实例指针->*成员函数指针)()的语法,括号不能少
方案二:使用std::function(更简洁灵活)
如果觉得成员函数指针语法太繁琐,可以用std::function包装函数对象,同时结合lambda或std::bind来绑定实例,代码可读性更高:
#include <iostream> #include <vector> #include <functional> // 必须包含这个头文件 struct previous_neuron_struct { double weight; std::function<double()> return_func; // 包装无参返回double的函数 }; class neuron { public: double value; std::vector<previous_neuron_struct> previous_neurons_vector; double Return_Value() { return value; } }; int main() { neuron neuron1; neuron neuron2; neuron2.value = 3.14; previous_neuron_struct* temp = new previous_neuron_struct; temp->weight = 0.5; // 用lambda绑定neuron2实例,直接返回它的Return_Value结果 temp->return_func = [&neuron2]() { return neuron2.Return_Value(); }; // 或者用std::bind的方式:temp->return_func = std::bind(&neuron::Return_Value, &neuron2); // 调用非常简单,直接调用函数对象 double result = temp->return_func(); std::cout << "调用结果:" << result << std::endl; delete temp; return 0; }
这种方式更适合神经网络场景,后续如果需要修改函数逻辑或者绑定不同类型的调用,灵活性更高。
为什么你的原代码报错?
temp->funcPtr = neuron2.Return_Value;:这里的neuron2.Return_Value是调用函数并获取返回值,而不是取函数地址,编译器会试图把double类型的返回值赋值给函数指针,自然报错。neuron2.*Return_Value:这种语法完全错误,成员函数指针的正确获取方式只能是&neuron::Return_Value,不能通过对象实例来引用未限定的成员函数名。
内容的提问来源于stack exchange,提问作者Owen
相关产品推荐
相关产品推荐

