首页 > 编程语言 >浅聊以下C++友元函数

浅聊以下C++友元函数

时间:2024-12-01 14:32:12浏览次数:11  
标签:友元 函数 浅聊 int C++ print class 友元类

目录

一、创建友元

二、友元函数的特点 

        1、一个函数可以是多个类的友元函数

        2、友元类中的成员函数都可以是另⼀个类的友元函数 

        3、友元类的关系是单向的

        4、友元类关系不能传递 


一、创建友元

        C++会控制类对象私有成员的访问。通常,在类中提供共有方法是唯一的访问途径,但是有时候这种限制太严格了,以致于会产生一些困扰。因此C++提供了⼀种突破类访问限定符封装的方式:友元

友元分为3种:

  • 友元函数
  • 友元类
  • 友元成员函数

通过让函数成为类的友元,可以赋予该函数与类的成员函数有相同的权限

         示例:

class Test
{
	//声明友元函数
	friend void print(Test& t);
public:
	Test(int n = 1)
		:num(n)
	{
	}
private:
	int num;
};
void print(Test& t)
{
	cout << t.num << endl;
}
int main() 
{
	Test t = 100;
	print(t);
	return 0;
}

        结果:

        虽然成员变量【num】是【Test】类的私有成员变量,但是通过让函数【print】成为类的友元,可以赋予该函数与类的成员函数有相同的权限,因此可以直接访问私有成员变量【num】

二、友元函数的特点 

友元函数的特点:

  1. 外部友元函数可访问类的私有和保护成员,友元函数仅仅是⼀种声明,他不是类的成员函数
  2. 友元函数可以在类定义的任何地⽅声明,不受类访问限定符限制
  3. ⼀个函数可以是多个类的友元函数
  4. 友元类中的成员函数都可以是另⼀个类的友元函数,都可以访问另⼀个类中的私有和保护成员
  5. 友元类的关系是单向的,不具有交换性,⽐如A类是B类的友元,但是B类不是A类的友元
  6. 友元类关系不能传递,如果A是B的友元, B是C的友元,但是A不是C的友元 

        1、一个函数可以是多个类的友元函数

        示例:

class B;
class A
{
	//一个函数可以是多个类的友元函数
	friend void print(A& a, B& b);
public:
	A(int n = 1)
		:_a(n)
	{}
private:
	int _a;
};

class B
{
	//一个函数可以是多个类的友元函数
	friend void print(A& a, B& b);
public:
	B(int n = 1)
		:_b(n)
	{}
private:
	int _b;
};

//一个函数可以是多个类的友元函数
void print(A& a, B& b)
{
	cout << a._a << " " << b._b << endl;
}
int main()
{
	A aa = 100;
	B bb = 200;
	print(aa, bb);
	return 0;
}

         结果:

        2、友元类中的成员函数都可以是另⼀个类的友元函数 

        示例: 

class B;
class A
{
	//友元类
	friend class B;
public:
	A(int n = 1)
		:_a(n)
	{}
private:
	int _a;
};

class B
{
public:
	B(int n = 1)
		:_b(n)
	{}
	//友元类中的成员函数都可以是另⼀个类的友元函数
	void print(A& a)
	{
		cout << a._a << " " << _b << endl;
	}
private:
	int _b;
};
int main()
{
	A aa = 100;
	B bb = 200;
	bb.print(aa);
	return 0;
}

        结果: 

        因为友元类中的成员函数都可以是另⼀个类的友元函数,所以【B】中的【print】函数是【A】的友元函数,与类的成员函数有相同的权限,因此可以直接访问私有成员变量【_a】

        3、友元类的关系是单向的

        示例:

class B;
class A
{
	//友元类
	friend class B;
public:
	A(int n = 1)
		:_a(n)
	{}
	//友元类的关系是单向的,不具有交换性
	void print(B& b)
	{
		cout << _a << " " << b._b << endl;
	}
private:
	int _a;
};

class B
{
public:
	B(int n = 1)
		:_b(n)
	{}
private:
	int _b;
};

        结果:

        【B】是【A】的友元类,但是【A】不是【B】的友元类,因此【A】中的函数不是【B】中的友元函数,不具有访问【B】类中私有成员权限 

        4、友元类关系不能传递 

        示例: 

class B;
class C;
class A
{
	//友元类
	friend class C;
public:
	A(int n = 1)
		:_a(n)
	{}
private:
	int _a;
};

class B
{
	//友元类
	friend class A;
public:
	B(int n = 1)
		:_b(n)
	{}
private:
	int _b;
};

class C
{
public:
	C(int n = 1)
		:_c(n)
	{}
	//友元类关系不能传递
	void print(B& b)
	{
		cout << b._b << endl;
	}
private:
	int _c;
};

         结果:

        【C】是【A】的友元类,【A】是【B】的友元类,但是友元类的关系不能传递因此【C】不是【B】的友元类,因此【C】中的函数不是【B】中的友元函数,不具有访问【B】类中私有成员权限 

三、小结

        友元有时提供了便利。但是友元会增加耦合度,破坏了封装,所以友元不宜多用,因为友元机制允许非成员函数访问私有成员变量

标签:友元,函数,浅聊,int,C++,print,class,友元类
From: https://blog.csdn.net/LVZHUO_2022/article/details/144155790

相关文章

  • C++编程:通过简单实现理解CyberRT的DataVisitor和DataDispatcher
    文章目录0.引言1.定义DataVisitor接口2.实现DataDispatcher3.创建具体的DataVisitor4.类关系图5.测试示例6.编译和运行0.引言本文简单实现类似CyberRT的DataVisitor和DataDispatcher,使得数据能够被分发给多个订阅者(访客)。1.定义DataVisitor接......
  • C++游戏开发:概念
    在数字娱乐产业蓬勃发展的今天,游戏开发已经成为了一个充满创意与挑战的领域。作为编程语言中的佼佼者,C++凭借其强大的性能、高度的灵活性和广泛的应用场景,在游戏开发中占据了举足轻重的地位。本文将从C++游戏开发的基础概念、关键技术、实战应用以及未来趋势等方面,进行详尽的探......
  • C++vector入门教程&函数执行细节(简单明了)
    目录一·vector介绍:二·vector的特征(优缺点)优点缺点三·vector的常用成员函数1·迭代器 2·容器 resizereserve 3·元素访问operator[]&at4·元素修改inserterase一·vector介绍:在学习vector之前需要明白一点vector底层是一个以数组实现的顺......
  • 2024年华为OD机试真题-矩阵扩散-C++-OD统一考试(E卷)
    最新华为OD机试考点合集:华为OD机试2024年真题题库(E卷+D卷+C卷)_华为od机试题库-CSDN博客     每一题都含有详细的解题思路和代码注释,精编c++、JAVA、Python三种语言解法。帮助每一位考生轻松、高效刷题。订阅后永久可看,发现新题及时跟新。题目描述:存在一个m*n的二维数......
  • 关联型容器(C++)
    setset是关联容器,含有键值类型对象的已排序集,搜索、移除和插入拥有对数复杂度。set内部通常采用红黑树实现。平衡二叉树的特性使得set非常适合处理需要同时兼顾查找、插入与删除的情况。和数学中的集合相似,set中不会出现值相同的元素。如果需要有相同元素的集合,需......
  • 【C++】程序流程控制(上)
    简介C/C++支持最基本的三种程序运行结构:顺序结构、选择结构、循环结构(1)顺序结构:程序按顺序执行,不发生跳转(2)选择结构:依据条件是否满足,有选择的执行相应功能(3)循环结构:依据条件是否满足,循环多次执行某段代码4.1选择结构4.1.1if语句作用:执行满足条件的语句if语句的三种形式......
  • 【C++】数据的输入、运算符(上)
    1.数据的输入作用:用于从键盘上获取数据关键字:cin语法:cin>>变量;例如:代码:#include<iostream>usingnamespace std;intmain(){   //整形数据   inta=0;   cout<<"请给整型变量a赋值:"<<endl;   cin>>a;   cout<<"整型变量a="......
  • C++命运石之门代码抉择:C++入门(下)
    文章目录4.C语言过渡到C++(下)4.1auto关键字(C++11)4.1.1为什么要用auto?4.1.2什么是auto?4.1.3auto的使用4.2基于范围的for循环(C++11)4.3指针空值nullptr(C++11)希望读者们多多三连支持小编会继续更新你们的鼓励就是我前进的动力!基于当前C++11的广......
  • 【C++】如何快速释放 vector 占用内存?
    1、前言        在C++编程实践中,std::vector作为一种灵活且高效的动态数组容器,广受欢迎。它能根据需求动态调整存储空间,但值得注意的是,当元素移除或容器清空后,其预留的内存容量(capacity)不会自动缩减。若对此现象不加留意,在频繁操作std::vector的情况下,可能会导致程序......
  • C++ 编程技巧之StrongType(1)
    最近看到一个NamedType的开源库,被里面的StrongType这个概念和里面的模版实现给秀了一脸,特此总结学习一下GitHub-joboccara/NamedType:ImplementationofstrongtypesinC++C++本身是一种强类型语言,类型包括int、double等这些buildin类型以及class类型,强类型的意思是......