C++基礎(chǔ)——函數(shù)

函數(shù)的定義

[修飾符] <返回類型> <函數(shù)名>(<形式參數(shù)列表>)[override] [const] [final]

??返回類型是必須的,當(dāng)沒有返回類型的時(shí)候就用void代替,如果參數(shù)個(gè)數(shù)超過1,則用逗號(hào)分隔參數(shù)列表,參數(shù)列表可以為空。

默認(rèn)參數(shù)

C++中可以在函數(shù)聲明時(shí)為參數(shù)提供一個(gè)默認(rèn)值,當(dāng)函數(shù)調(diào)用時(shí)沒有指定這個(gè)參數(shù)的值,編譯器會(huì)自動(dòng)用默認(rèn)值代替一旦在一個(gè)函數(shù)調(diào)用中開始使用默認(rèn)參數(shù)值,那么這個(gè)參數(shù)后的所有參數(shù)都必須使用默認(rèn)參數(shù)

void myPrint(int x = 3)
{
    printf("x:%d", x);
}

函數(shù)重載(Overroad)

??函數(shù)重載(Function Overload)用同一個(gè)函數(shù)名定義不同的函數(shù),當(dāng)函數(shù)名和不同的參數(shù)搭配時(shí)函數(shù)的含義不同。 函數(shù)重載至少滿足下面的一個(gè)條件:1.參數(shù)個(gè)數(shù)不同。 2.參數(shù)類型不同。3.參數(shù)順序不同。

class foo
{
public:
    int add(int a,int b)
    {
        return  a+b;
    }
    float add(float a, float b)
    {
        return  a+b;
    }
};

函數(shù)的返回值不作為區(qū)分重載函數(shù)的的條件。

float add(int a, int b)
    {
        return  a+b;
    } //編譯錯(cuò)誤

override

??如果不使用override,當(dāng)你手一抖,將foo()寫成了f00()會(huì)怎么樣呢?結(jié)果是編譯器并不會(huì)報(bào)錯(cuò),因?yàn)樗⒉恢滥愕哪康氖侵貙懱摵瘮?shù),而是把它當(dāng)成了新的函數(shù)。如果這個(gè)虛函數(shù)很重要的話,那就會(huì)對(duì)整個(gè)程序不利。所以,override的作用就出來了,它指定了子類的這個(gè)虛函數(shù)是重寫的父類的,如果你名字不小心打錯(cuò)了的話,編譯器是不會(huì)編譯通過的.

class A
{
    virtual void foo();
};
class B :public A
{
     //void fo0();
     void fo0() override; //會(huì)編譯報(bào)錯(cuò)
};

virtual 虛函數(shù)

??被virtual關(guān)鍵字修飾的成員函數(shù),就是虛函數(shù)。虛函數(shù)的作用,用專業(yè)術(shù)語來解釋就是實(shí)現(xiàn)多態(tài)性 (Polymorphism),多態(tài)性是將接口與實(shí)現(xiàn)進(jìn)行分離,虛函數(shù)是C++ 的多態(tài)性的主要體現(xiàn),指向基類的指針在操作它的多態(tài)類對(duì)象時(shí),會(huì)根據(jù)不同的類對(duì)象,調(diào)用其相應(yīng)的函數(shù)。

class Parent {
public:
    void func_one(){
        cout<<"parent:func_one"<<endl;
    }
    virtual void func_two(){
        cout<<"parent:func_two"<<endl;
    }
};

class Child : public Parent{
public:
   void func_one(){
       cout<<"Child:func_one"<<endl;
   }
    virtual void func_two(){
        cout<<"Child:func_two"<<endl;
    }
};


int main() {
    Child child;
    Parent *c= &child;//指向子類的指針
    c->func_one();
    c->func_two();
    Parent &p = child;//子類的引用
    p.func_one();
    p.func_two();
    return 0;
}
打印結(jié)果:
parent:func_one
Child:func_two
parent:func_one
Child:func_two

??簡(jiǎn)單總結(jié)就是:基類中將某方法定義為虛函數(shù),則在派生類中,該方法仍為虛方法。在使用時(shí),定義基類類型的指針,使其指向派生類的對(duì)象,使用該指針調(diào)用某個(gè)方法,若該方法未被聲明為虛函數(shù),則調(diào)用的是指針類中的方法,若該方法是虛函數(shù),則調(diào)用的是指針指向?qū)ο箢愔械脑摲椒?。這也即是動(dòng)態(tài)聯(lián)編。
虛函數(shù)使用原則:
1)當(dāng)類不會(huì)用作基類時(shí),成員函數(shù)不要聲明為virtual
2)當(dāng)成員函數(shù)不重新定義基類的方法,成員函數(shù)不要聲明為virtual

inline內(nèi)聯(lián)函數(shù)

??內(nèi)聯(lián)函數(shù)由 編譯器處理,直接將編譯后的函數(shù)體插入調(diào)用的地方。宏代碼片段 由預(yù)處理器處理, 進(jìn)行簡(jiǎn)單的文本替換,沒有任何編譯過程

#include "iostream"
using namespace std;
#define MYFUNC(a, b) ((a) < (b) ? (a) : (b))  

inline int myfunc(int a, int b) 
{
    return a < b ? a : b;
}

int main()
{
    int a = 1;
    int b = 3;
    //int c = myfunc(++a, b);  //頭疼系統(tǒng)
    int c = MYFUNC(++a, b);  

    printf("a = %d\n", a); 
    printf("b = %d\n", b);
    printf("c = %d\n", c);

system("pause");
    return 0;
}

??編譯器對(duì)于內(nèi)聯(lián)函數(shù)的限制并不是絕對(duì)的,內(nèi)聯(lián)函數(shù)相對(duì)于普通函數(shù)的優(yōu)勢(shì)只是省去了函數(shù)調(diào)用時(shí)壓棧,跳轉(zhuǎn)和返回的開銷。因此,當(dāng)函數(shù)體的執(zhí)行開銷遠(yuǎn)大于壓棧,跳轉(zhuǎn)和返回所用的開銷時(shí),那么內(nèi)聯(lián)將無意義。C++中內(nèi)聯(lián)編譯的限制:
1.不能存在任何形式的循環(huán)語句 2.不能存在過多的條件判斷語句 3.函數(shù)體不能過于龐大 4.不能對(duì)函數(shù)進(jìn)行取址操作 5.函數(shù)內(nèi)聯(lián)聲明必須在調(diào)用語句之前。

靜態(tài)成員函數(shù)

??靜態(tài)成員函數(shù)數(shù)添加關(guān)鍵字static,類的靜態(tài)成員(變量和方法)屬于類本身,在類加載的時(shí)候就會(huì)分配內(nèi)存,可以通過類名直接去訪問;非靜態(tài)成員(變量和方法)屬于類的對(duì)象,所以只有在類的對(duì)象產(chǎn)生(創(chuàng)建類的實(shí)例)時(shí)才會(huì)分配內(nèi)存,然后通過類的對(duì)象(實(shí)例)去訪問。調(diào)用靜態(tài)成員函數(shù)如下:

<類名>::<靜態(tài)成員名>

??因?yàn)殪o態(tài)成員函數(shù)屬于整個(gè)類,在類實(shí)例化對(duì)象之前就已經(jīng)分配空間了,而類的非靜態(tài)成員必須在類實(shí)例化對(duì)象后才有內(nèi)存空間,所以靜態(tài)成員函數(shù)中,不能使用普通變量和成員函數(shù),靜態(tài)成員函數(shù)與非靜態(tài)成員函數(shù)的根本區(qū)別是:非靜態(tài)成員函數(shù)有 this 指針,而靜態(tài)成員函數(shù)沒有 this 指針。

private:
    int x;
public:
    static void output()
        {
        cout<<x<<endl;
    }
};
//error: invalid use of member 'x' in static member function

友元函數(shù)

friend <返回類型> <函數(shù)名> (<參數(shù)列表>);

??友元函數(shù)是可以直接訪問類的私有成員的非成員函數(shù)。它是定義在類外的普通函數(shù),它不屬于任何類,但需要在類的定義中加以聲明,聲明時(shí)只需在友元的名稱前加上關(guān)鍵字friend。
??需要注意的是友元函數(shù)不是成員函數(shù),卻可以訪問類中的私有成員。友元的作用在于提高程序的運(yùn)行效率(即減少了類型檢查和安全性檢查等都需要的時(shí)間開銷),同時(shí)它破壞了類的封裝性和隱藏性,使得非成員函數(shù)可以訪問類的私有成員。

Point::Point(int currX, int currY)
{
    x = currX;
    y = currY;
}

double  distance(const Point &a,const Point &b)
{
    double length;
    length=sqrt((a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y));     //它可以引用類中的私有成員
    return length;
}

int main()
{
    Point p1(0,3), p2(4,0);
    cout<<distance(p1,p2)<<endl;
}
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖,帶你破解...
    沈念sama閱讀 230,247評(píng)論 6 543
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 99,520評(píng)論 3 429
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人,你說我怎么就攤上這事?!?“怎么了?”我有些...
    開封第一講書人閱讀 178,362評(píng)論 0 383
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)。 經(jīng)常有香客問我,道長(zhǎng),這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 63,805評(píng)論 1 317
  • 正文 為了忘掉前任,我火速辦了婚禮,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘。我一直安慰自己,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 72,541評(píng)論 6 412
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著,像睡著了一般。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 55,896評(píng)論 1 328
  • 那天,我揣著相機(jī)與錄音,去河邊找鬼。 笑死,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播,決...
    沈念sama閱讀 43,887評(píng)論 3 447
  • 文/蒼蘭香墨 我猛地睜開眼,長(zhǎng)吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 43,062評(píng)論 0 290
  • 序言:老撾萬榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎,沒想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 49,608評(píng)論 1 336
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 41,356評(píng)論 3 358
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 43,555評(píng)論 1 374
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情,我是刑警寧澤,帶...
    沈念sama閱讀 39,077評(píng)論 5 364
  • 正文 年R本政府宣布,位于F島的核電站,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 44,769評(píng)論 3 349
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 35,175評(píng)論 0 28
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 36,489評(píng)論 1 295
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 52,289評(píng)論 3 400
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 48,516評(píng)論 2 379

推薦閱讀更多精彩內(nèi)容