但不鼓励……;height(h);'B');char cup = *(char*)((int*)&int weight = *((int*)&<当然除了内存对齐;还有可能有虚函数;#include <public;weight(w);private;};'B');Actor actor = *((Actor*)&
想知道怎么不使用friend,访问private的成员变量?
有方法,但不鼓励……
方法一
#include <iostream> using namespace std; class Sensei { public: Sensei(int h, int w, char c):height(h), weight(w), cup(c) {} private: int height; int weight; char cup; }; int main() { Sensei sensei(160, 80, 'B'); int height = *(int*)&sensei; int weight = *((int*)&sensei + 1); char cup = *(char*)((int*)&sensei + 2); cout<<height<<endl; cout<<weight<<endl; cout<<cup<<endl; }
当存在内存对齐的时候,这个代码未必有效。主要就是手撸的内存偏移就不准了。当然如果你知道你的编译器是怎么个对齐规则,你也可以继续用。比如我们调换cup和weight的顺序。
#include <iostream> using namespace std; class Sensei { public: Sensei(int h, int w, char c):height(h), weight(w), cup(c) {} private: int height; char cup; int weight; }; int main() { Sensei sensei(160, 80, 'B'); int height = *(int*)&sensei; char cup = *(char*)((int*)&sensei + 1); int weight = *((int*)&sensei + 2); cout<<height<<endl; cout<<weight<<endl; cout<<cup<<endl; }
在我们机器上是4字节对齐的,所以虽然cup是char类型,但是会空余3个byte之后才是weight。
当然除了内存对齐,还有可能有虚函数,占用额外内存空间。不过你既然已经能看到这了,说明自己清楚内存布局的各种问题,自己手撸吧,不介绍了。本身这个文章也是不鼓励实际应用的,仅供延伸思路。
方法二
定义一个同样字段的类(主要是字段类型和顺序要相同)来强制类型转换。
#include <iostream> using namespace std; class Sensei { public: Sensei(int h, int w, char c):height(h), weight(w), cup(c) {} private: int height; char cup; int weight; }; struct Actor { int height; char cup; int weight; }; int main() { Sensei sensei(160, 80, 'B'); Actor actor = *((Actor*)&sensei); // 或者 //Actor actor = *(reinterpret_cast<Actor*>(&sensei)); cout<<actor.height<<endl; cout<<actor.weight<<endl; cout<<actor.cup<<endl; }
方法三
方法三,比较Trick了。但比前两种反而有使用场景。比如我们要做UT(单元测试)的时候,测试类的某些数据成员是private的,并且没提供对外set的方法。但我们想hack一些数据进去,做测试。这时候这个Sensei类的定义是在一个独立头文件中,比如sensei.h。我们在ut的的cpp或头文件中include它,这种情况都不需要像前面两种那样脱裤子放屁。
// sensei.h class Sensei { public: Sensei(int h, int w, char c):height(h), weight(w), cup(c) {} private: int height; char cup; int weight; };
我们直接用宏替换就好了,把private替换成public。并且这个其实也是做ut时候的常规做法……
// test_sensei.cpp #include <iostream> using namespace std; #define private public #include "sensei.h" #undef private int main() { Sensei sensei(160, 80, 'B'); cout<<sensei.height<<endl; cout<<sensei.cup<<endl; cout<<sensei.weight<<endl; return 0; }
原文地址:https://cloud.tencent.com/developer/article/1915040
评论列表