将对象的方法指针传递给接受[静态方法指针/全局函数]指针的函数
Posted
技术标签:
【中文标题】将对象的方法指针传递给接受[静态方法指针/全局函数]指针的函数【英文标题】:Passing object's method pointer to function that accept [static method pointer / global function ] pointer 【发布时间】:2013-12-13 10:54:08 【问题描述】:我有方法
typedef void
(* JSErrorReporter)(JSContext *cx, const char *message, JSErrorReport *report);
JS_SetErrorReporter(JSContext *cx, JSErrorReporter er);
我想传递对象的方法而不是静态方法
JS_SetErrorReporter(cx,this->Reporter);//Failed !
其中 Reporter 是对象的方法(不是静态的)
JS_SetErrorReporter(cx,Reporter); //Passed
其中 Reporter 是静态方法,声明为
static void SomeClass::reportError(JSContext *cx, const char *message, JSErrorReport *report)
【问题讨论】:
使用&SomeClass::reportError
那么,this->Reporter
是完全错误的语法(即使对于成员函数指针)。静态方法无论如何都不知道this
。
你可以做的是提供一个静态方法,它以某种方式从上下文中获取this
指针。我不知道JSContext
是否提供了一些void* userData;
成员,可以用于此。
【参考方案1】:
你想使用一个成员函数指针,你必须得到正确的语法,(不是微不足道的) 对于一个无聊的函数,获取并返回一个 int,那就是:
声明一个变量(也适用于参数):
int (SomeClass::*my_memfunc_ptr)(int);
分配一个变量:
my_memfunc_ptr = &SomeClass::some_member_func;
调用:
SomeClass *x = new SomeClass;
int n = (x->*my_memfunc_ptr)(6);
我把这个适应你的非 int 用途留给你。
【讨论】:
【参考方案2】:你不能直接做。因为要调用一些非静态函数,你必须有 this
指针,但你不要将它传递给 JS_SetErrorReporter
函数。
两种可能的解决方案:
更改JSErrorReporter
签名以接受void *
类型的+1 参数并在那里传递this
指针。
创建一个包装函数作为一个全局函数,它也知道需要this
指针。
【讨论】:
【参考方案3】:避免静态函数很容易使用 __closure 函数指针来代替:
//---------------------------------------------------------------------------
class C2
public:
void callback1() // your member function to pass to ...
;
class C1 // some class with member function pointer usage
public:
void (__closure *callback1)(); // member function pointer
C1() callback1=NULL; // constructor
void do_something() // some function with use of callback1
if (callback1) callback1();
;
void some_function(void (__closure *f)()) // some function with member function parameter usage
if (f) f();
void main()
C1 c1;
C2 c2;
c1.callback1=c2.callback1;
c1.do_something();
some_function(c1.callback1);
some_function(c2.callback1);
//---------------------------------------------------------------------------
[编辑 1]
但正如 RichardPlunkett 概述的 __closure 它仅适用于 borland/embarcadero 编译器 对于 VC/GCC/Intel ... 编译器,您需要一种解决方法 那里有一些。 看起来人们更喜欢名为 boost 库的东西 在这里我找到了一个__closure 模仿的例子http://www.rsdn.ru/forum/cpp/3078740.flat 它是俄文的,但即使对于我们 azbuka 非读者来说,源代码也很清楚......【讨论】:
那是编译器特定的扩展不是吗? 如果你是对的,我认为这是理所当然的,因为我主要在 borland 编写代码,所以我没有想到 :(objectmix.com/c/398370-how-translate-__closure-into-pure-c.html以上是关于将对象的方法指针传递给接受[静态方法指针/全局函数]指针的函数的主要内容,如果未能解决你的问题,请参考以下文章