指针的地址“this”在指向成员函数调用的指针内意外更改

编程入门 行业动态 更新时间:2024-10-19 09:46:05
本文介绍了指针的地址“this”在指向成员函数调用的指针内意外更改的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧! 问题描述

我有问题的指针成员函数调用。在函数指针调用之外的指针this的地址与调用内部不同,因此对类变量的所有访问都会导致错误的值。

我在这里包含代码。

class ClassInterface { public: ClassInterface(void); 〜ClassInterface(void); }; class ClassA:public ClassInterface { public: float _a; public: ClassA(void); 〜ClassA(void); virtual void Update(); }; class ClassB:public ClassA { public: ClassB(void); 〜ClassB(void); void Update(); void ProcessTaskB(void *); }; //ClassB.CPP void ClassB :: ProcessTaskB(void *) { printf(ClassB :: ProcessTaskB\\\); printf(myB INSIDE callback的地址=%d \\\,this); _a + = 100; } //测试CPP #includestdafx.h #includeClassInterface.h #includeClassA.h #includeClassB.h typedef void(ClassInterface :: * Callback)(void *); int _tmain(int argc,_TCHAR * argv []) { ClassA * myA = new ClassA(); ClassB * myB = new ClassB(); 回调fptrB =(回调)&(ClassB :: ProcessTaskB); printf(myB outside callback =%d\\\的地址,myB); (myB-> * fptrB)(NULL); return 0; }

p>

myB OUTSIDE回调的地址= 1332696 myB INSIDE回调的地址= 1332700

因此语句_a + = 100;不改变_a。它改变了地址(& _a + 4)。

我没有办法解决这个问题。请帮助我修复。

解决方案

在更新的表单中,代码是完全正确的,没有任何问题。对不正确行为的唯一解释是,你必须在一些限制成员指针模型(在一般情况下不正确工作)中使用MSVC ++编译器。事实上,我相信MSVC ++编译器在尝试转换成员指针时会发出相应的警告。

无论如何,添加

pragma pointers_to_members(full_generality,virtual_inheritance)

为了启用成员函数指针的完整功能通过C ++标准,你的代码应该工作得很好。

#pragma pointers_to_members(full_generality,multiple_inheritance)

应该足够了。与 / vmm,/ vms,/ vmv 组合的编译器选项与 / vmg 组合实现相同的效果。 p>

此外,在这种上下文中避免使用C风格的转换。正在使用的转换由 static_cast

执行回调fptrB = static_cast< ; Callback>(& ClassB :: ProcessTaskB);

此外,请勿尝试使用%d 格式说明符在 printf 中。这是另一个未定义的行为。打印指针是%p 的格式说明符。

I have problem with the pointer to member function call. The address of pointer "this" outside the function pointer call is different than inside the call thus all access to the class variables results wrong values.

I include the code here.

class ClassInterface { public: ClassInterface(void); ~ClassInterface(void); }; class ClassA:public ClassInterface { public: float _a; public: ClassA(void); ~ClassA(void); virtual void Update(); }; class ClassB:public ClassA { public: ClassB(void); ~ClassB(void); void Update(); void ProcessTaskB(void*); }; //ClassB.CPP void ClassB::ProcessTaskB(void*) { printf("ClassB::ProcessTaskB\n"); printf("Address of myB INSIDE callback = %d\n",this); _a += 100; } //test CPP #include "stdafx.h" #include "ClassInterface.h" #include "ClassA.h" #include "ClassB.h" typedef void (ClassInterface::*Callback) (void* ); int _tmain(int argc, _TCHAR* argv[]) { ClassA* myA = new ClassA(); ClassB* myB = new ClassB(); Callback fptrB = (Callback) &(ClassB::ProcessTaskB); printf("Address of myB outside callback = %d\n",myB); (myB->*fptrB)(NULL); return 0; }

And this is the output:

Address of myB OUTSIDE callback = 1332696 Address of myB INSIDE callback = 1332700

Thus the statement _a += 100; does not make change to _a. It made change to address (&_a + 4).

I have no clue to resolve this. Please help me fix.

解决方案

In your updated form your code is perfectly correct and has no problems whatsoever. The only explanation for the incorrect behavior is that you must be using MSVC++ compiler in some "restricted" member pointer model (which works incorrectly in general case). In fact, I believe MSVC++ compiler issues the corresponding warnings when you attempt to convert your member pointers. Did you just ignore the warning?

Anyway, add

#pragma pointers_to_members( full_generality, virtual_inheritance )

to you code in order to enable full functionality of member function pointers required by C++ standard, and your code should work fine. In your case this

#pragma pointers_to_members( full_generality, multiple_inheritance )

should be sufficient though. Compiler options from /vmm, /vms, /vmv group in combination with /vmg achieve the same effect.

Also, avoid C-style casts in such contexts. The conversion you are using is performed by static_cast

Callback fptrB = static_cast<Callback>(&ClassB::ProcessTaskB);

Also, don't attempt to print pointers with %d format specifier in printf. This is another undefined behavior right there. Printing pointers is what %p format specifier is for.

更多推荐

指针的地址“this”在指向成员函数调用的指针内意外更改

本文发布于:2023-07-29 00:44:36,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1235658.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:指针   函数   意外   成员   地址

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!