如何在不使用 C++ 中的友元函数的情况下访问私有变量
how to access private variables with out using friend function in c++
#include <iostream>
using namespace std;
class Point
{
friend void ChangePrivate( Point & );
public:
Point( void ) : m_i(0) {}
void PrintPrivate( void ){cout << m_i << endl; }
private:
int m_i;
};
void ChangePrivate ( Point &i ) { i.m_i++; }
int main()
{
Point sPoint;
sPoint.PrintPrivate();
ChangePrivate(sPoint);
sPoint.PrintPrivate();
}
这是示例如何使用友元函数访问私有变量如何在不使用友元函数的情况下使用?
关键字friend
专门用于绕过private
施加的访问限制并protected
访问控制。
如果您想在不使用 friend
的情况下访问私有变量,请将公共访问器添加到类本身:这是访问私有变量的最常见和最预期的方式:
class Point
{
public:
Point( void ) : m_i(0) {}
void PrintPrivate( void ){cout << m_i << endl; }
int getI() {return m_i;}
void setI(int _i) {m_i = _i;}
private:
int m_i;
};
...
Point sPoint;
sPoint.setI(sPoint.getI()+1);
这是一个符合标准的黑客(来源(:
template<typename Tag, typename Tag::type M>
struct Rob {
friend typename Tag::type get(Tag) {
return M;
}
};
class Point
{
public:
Point( void ) : m_i(0) {}
void PrintPrivate( void ){cout << m_i << endl; }
private:
int m_i;
};
struct Point_f {
typedef int Point::*type;
friend type get(Point_f);
};
template struct Rob<Point_f, &Point::m_i>;
void ChangePrivate ( Point &i )
{
i.*get(Point_f()) = 4;
}
在 ideone 上采样。
访问控制不适用于显式模板实例化的参数 ( [temp.explicit]/12
(。这可以用来向私人成员提供公共访问权限(由 litb 提供(:
首先是一些设置代码:
template<typename Tag>
struct result {
/* export it ... */
typedef typename Tag::type type;
static type ptr;
};
template<typename Tag>
typename result<Tag>::type result<Tag>::ptr;
template<typename Tag, typename Tag::type p>
struct rob : result<Tag> {
/* fill it ... */
struct filler {
filler() { result<Tag>::ptr = p; }
};
static filler filler_obj;
};
template<typename Tag, typename Tag::type p>
typename rob<Tag, p>::filler rob<Tag, p>::filler_obj;
现在Point
的定义:
class Point
{
public:
Point() : m_i(0) {}
void PrintPrivate(){cout << m_i << endl; }
private:
int m_i;
};
现在通过显式实例化rob<Pointm_i, &Point::m_i>
来填充result<Pointm_i>::ptr
- 这是一个显式模板实例化,因此访问控制不适用:
struct Pointm_i { typedef int Point::*type; };
template class rob<Pointm_i, &Point::m_i>;
并访问私有成员:
void ChangePrivate ( Point &i ) { (i.*result<Pointm_i>::ptr)++; }
int main()
{
Point sPoint;
sPoint.PrintPrivate();
ChangePrivate(sPoint);
sPoint.PrintPrivate();
}
void ChangePrivate ( Point &i ) { *(int*)( ((char*)&i) + 0 ) += 1; }
如果适用或自定义计算的偏移量,请将 0 替换为 offsetof((。
或类似的东西
struct HackPoint
{
int m_i;
};
void ChangePrivate ( Point &i ) { ((HackPoint*)(void*)&i)->m_i++; }
试试这个
*(int*)(&sPoint) += 1;
而不是
ChangePrivate(sPoint);
但这不是一种好的编码风格,只是为了好玩。
C++对象模型内部 本书对对象模型进行了详细的分析C++
相关文章:
- C++模板来检查友元函数的存在
- 如何使用单独文件中的派生类访问友元函数对象
- 模板化的类和友元函数
- 友元函数无法访问私有数据成员 (c++)
- 继承和友元函数,从基类访问受保护的成员
- 如何在友元函数中使用静态成员而不添加前缀 [类名]::
- 在将函数声明为友元时,尖括号的含义是什么?
- 在模板类之外定义友元函数的正确方法是什么?
- 2个模板化类的非模板友元函数未定义引用错误
- C++ 友元函数和私有构造函数
- 使第二个类的构造函数成为第一个类中的友元函数
- 未定义的类模板不会实例化以检查友元函数
- C++类中的友元函数有问题?
- 使用typedef'ed返回类型声明友元函数时出现编译器错误
- 模板类中的模板友元函数
- C++ 17 个友元函数声明和内联命名空间
- 将派生类的构造函数声明为父类的友元
- 友元函数需要一个帮助程序函数
- 在基/派生类的成员函数/友元函数中派生* 到 Base* 的转换
- 模板类的非模板函数友元