当前位置: 首页 > news >正文

【C++】解析friend关键字:概念、友元函数与类的使用

前言

在 C++ 中,friend 关键字用于允许非成员函数或其他类访问类的私有成员和保护成员。需要谨慎使用,确保代码的封装性和维护性。


1. 基本概念

friend 关键字可以用来声明以下几种情况:

  • 友元函数(Friend Functions):非成员函数可以成为某个类的友元,从而访问该类的私有和保护成员。
  • 友元类(Friend Classes):一个类可以成为另一个类的友元,从而允许访问其私有和保护成员。
  • 友元成员函数(Friend Member Functions):其他类的成员函数也可以被声明为友元,从而访问类的私有和保护成员。

2. 友元函数

友元函数是一个非成员函数,但它可以访问类的私有成员和保护成员。声明友元函数的语法如下:

class MyClass {
private:int privateData;
public:MyClass() : privateData(0) {}// 声明友元函数friend void showData(const MyClass& obj);
};// 定义友元函数
void showData(const MyClass& obj) {std::cout << "Private data: " << obj.privateData << std::endl;
}

在上面的例子中,showData 函数被声明为 MyClass 的友元函数,因此它可以访问 privateData 成员。


3. 友元类

友元类是一个类,它可以访问另一个类的私有和保护成员。声明友元类的语法如下:

class MyClassB; // 前向声明class MyClassA {
private:int privateData;
public:MyClassA() : privateData(42) {}// 声明 MyClassB 为友元类friend class MyClassB;
};class MyClassB {
public:void display(const MyClassA& obj) {std::cout << "Private data from MyClassA: " << obj.privateData << std::endl;}
};

在上面的例子中,MyClassB 被声明为 MyClassA 的友元类,因此 MyClassB 可以访问 MyClassAprivateData 成员。


4. 友元成员函数

如果你希望其他类的某个特定成员函数可以访问类的私有和保护成员,可以声明这个成员函数为友元:

class MyClassC;class MyClassA {
private:int privateData;
public:MyClassA() : privateData(99) {}// 声明 MyClassC 的成员函数 foo 为友元friend void MyClassC::foo(const MyClassA& obj);
};class MyClassC {
public:void foo(const MyClassA& obj) {std::cout << "Private data from MyClassA: " << obj.privateData << std::endl;}
};

在这个例子中,MyClassC 的成员函数 foo 被声明为 MyClassA 的友元,因此 foo 可以访问 MyClassAprivateData 成员。


5. 使用 friend 的注意事项

  • 封装性:过度使用友元可能会破坏类的封装性,因此应该谨慎使用。
  • 友元函数的访问权限:友元函数本身不具有类的成员权限,它仅仅是一个非成员函数,但拥有类的访问权限。
  • 友元声明位置:友元声明通常放在类的声明内部,以确保它们的访问权限是明确的。

通过正确使用 friend 关键字,你可以实现灵活的类间访问控制,但也要平衡好代码的封装性和访问需求。


http://www.mrgr.cn/news/17261.html

相关文章:

  • 网络安全入门教程(非常详细)从零基础入门到精通,看完这一篇就够了。
  • 八、百度到的--centos安装artifactory--没什么用
  • 数据集格式转化
  • 《机器学习》周志华-CH5(神经网络)
  • 将二叉搜索树转化为排序的双向链表
  • Java 异常架构Exception(异常)
  • 操作符详解(下)
  • 【微机原理】指令JZ和JNZ的区别
  • How to run a JAR file
  • 龙芯+FreeRTOS+LVGL实战笔记(新)——00关于本专栏
  • 干货分享|分享一款高效的软件卸载神器 Geek Uninstaller
  • 四足机器人控制算法——建模、控制与实践(unitree_guide配置)
  • ubuntu环境快速安装mysql
  • 浅析Java线程池实现原理
  • Java注解和JDK新特性
  • Python爬虫案例四:爬取某个博主的所有文章保存成PDF格式
  • C++11 可变参数模板
  • 两个月冲刺软考——求解关系模式达到了第几范式题型(例题+讲解,一看就会)
  • Linux 进程概念
  • 集成电路学习:什么是GUI图形用户界面