淺談友元和static成員
友元和static成員
- 前言
- 一、友元
- 1.友元函式
- 2.友元類
- 二、static
- 總結
前言
在說這兩個之前,我們再掰扯一下建構式,之前我們在“淺談六個成員函式”中提到了引數串列初始化,

又叫“初始化串列”,
用法:以冒號開始,接著是逗號分隔的資料成員串列,每個成員變數后面跟著放在括號中的初始值或運算式,
注:
1.每個成員變數在初始化串列中只能出現一次;
2.類中若包含:參考成員變數、const成員變數、自定義型別成員,則必須使用初始化串列進行初始化;
3.成員變數在類中的宣告次序就是其在初始化串列中的初始化順序,與其在初始化串列中的先后次序無關,
提示:以下是本篇文章正文內容
一、友元
在大學生活中,我們經常要交一些實驗報告,這使我們很頭疼,基本上每個宿舍都會有“那個男人”站出來寫報告,然后其他人把報告改個學號姓名上交,友元就相當于這些白piao的舍友一樣,
友元分為:友元函式和友元類
友元提供了一種突破封裝的方式,有時提供了便利,但是友元會增加耦合度,這不符合我們的“高內聚,低耦合”的思想,破壞了封裝,所以友元不宜多用,
1.友元函式
例如當我們想多載“<<”或“>>”時,發現我們無法將operator<<多載成成員函式,因為cout輸出流物件和成員函式隱含的this指標在搶占第一個引數的位置,this指標默認是第一個引數也就是“<<”的左運算元,但是實際使用中cout需要是第一個形參物件,才能正常使用,因此我們只能將operator<<多載為非成員函式,比如全域函式,但是這樣的話又不能訪問成員變數,友元函式便可以完美解決這個問題,
class Date
{
friend ostream& operator<<(ostream& out, const Date& d);
friend istream& operator>>(istream& in, Date& d);
public:
Date(int year, int month, int day) :m_year(year), m_month(month), m_day(day)
{}
private:
int m_year;
int m_month;
int m_day;
};
ostream& operator<<(ostream& out, const Date& d)//以參考回傳可以連續輸出
{
out << d.m_year << "-" << d.m_month << "-" << d.m_day;
return out;
}
istream& operator>>(istream& in, Date& d)
{
in >> d.m_year;
in >> d.m_month;
in >> d.m_day;
return in;
}
友元函式可以直接訪問類的私有成員,它不屬于任何類,需要在類里面用friend關鍵字宣告,

特征:
1.友元函式可訪問類的私有和保護成員,但不是類的成員函式;
2.友元函式不能用const修飾;
3.友元函式可以在類定義的任何地方宣告,不受類訪問限定符限制;
4.一個函式可以是多個類的友元函式;
5.友元函式的呼叫與普通函式呼叫原理相同,
2.友元類
和友元函式意義差不多,友元類的所有成員函式都可以是另一個類的友元函式,都可以訪問類一個類的私有成員,
class Time
{
friend class Date;//代表Date類是Time的友元類,
public:
Time(int hour = 0, int minute = 0, int second = 0)
:m_hour(hour), m_minute(minute), m_second(second)
{}
private:
int m_hour;
int m_minute;
int m_second;
};
class Date
{
public:
Date(int year, int month, int day) :m_year(year), m_month(month), m_day(day)
{}
private:
int m_year;
int m_month;
int m_day;
Time t;//前提是Time類中有默認建構式(全預設構造也為默認構造);
public:
void DatesetTime(int hour, int minute, int second)
{
t.m_hour = hour;
t.m_minute = minute;
t.m_second = second;
}
};
特征:
1.友元關系是單向的;
2.友元關系不能傳遞;
二、static
宣告為static的類成員為類的靜態成員,用static修飾的成員變數,稱之為靜態成員變數;用static修飾的成員函式,稱之為靜態成員函式,靜態的成員變數一定要在類外進行初始化,
劍指offer64題:求1+2+…+n,要求不能使用乘除、for、while、、if、switch等關鍵字及條件判斷陳述句,
class Solution {
public:
class Sum
{
public:
Sum()
{
_sum += _i;
_i++;
}
};
int Sum_Solution(int n) {
_i = 1;
_sum = 0;
Sum array[n];
return _sum;
}
static size_t _sum;
static size_t _i;
};
size_t Solution::_sum = 0;
size_t Solution::_i = 1;
特征:
1.靜態成員為類物件所共享,不屬于某個具體的實體;
2.靜態成員變數必須在類外定義,定義時不添加static關鍵字;
3.類靜態成員即可用類名::靜態成員或者物件.靜態成員訪問;
4.靜態成員函式沒有隱藏的this指標(友元也沒有且級別低于靜態成員函式),不能訪問任何非靜態成員;
5.靜態成員和類的普通成員一樣,也有public、protected、private三種訪問級別,也可以具有回傳值;
6.普通成員函式可以呼叫靜態成員變數及靜態成員函式,而反之不能,
總結
朋友的朋友不一定是朋友;我拿你當朋友,你卻不讓我抄你作業,
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/271325.html
標籤:java
上一篇:super詳解(java)
