99偷拍视频精品区一区二,口述久久久久久久久久久久,国产精品夫妇激情啪发布,成人永久免费网站在线观看,国产精品高清免费在线,青青草在线观看视频观看,久久久久久国产一区,天天婷婷久久18禁,日韩动漫av在线播放直播

c++primer第7章類-創新互聯

文章目錄
  • 第7章 類
    • 7.1 定義抽象數據類型
      • 7.1.1 設計Sales_data類
      • 7.1.2 定義改進的Sales_data類
      • 7.1.3 定義類相關的非成員函數
      • 7.1.4 構造函數
      • 7.1.5 拷貝、賦值和析構
    • 7.2 訪問控制與封裝
      • 7.2.1 友元
    • 7.3 類的其他特性
      • 7.3.1 類成員再探
      • 7.3.2 返回*this的成員函數
      • 7.3.3 類類型
      • 7.3.4 友元再探
    • 7.4 類的作用域
      • 7.4.1 名字查找與類的作用域
    • 7.5 構造函數再探
      • 7.5.1 構造函數初始值列表
      • 7.5.2 委托構造函數
      • 7.5.3 默認構造函數的作用
      • 7.5.4 隱式的類類型轉換
      • 7.5.5 聚合類
      • 7.5.6 字面值常量類
      • 7.6 類的靜態成員
    • 小結
    • 術語表

成都創新互聯公司專業為企業提供迎江網站建設、迎江做網站、迎江網站設計、迎江網站制作等企業網站建設、網頁設計與制作、迎江企業網站模板建站服務,十年迎江做網站經驗,不只是建網站,更提供有價值的思路和整體網絡服務。第7章 類
  • 使用類定義自己的數據類型
  • 數據抽象
    • 將對象的具體實現與對象所能執行的操作分離開來
    • 依賴于接口和實現分離的編程技術
      • 接口:用戶所能執行的操作
      • 實現:類的數據成員、負責接口實現的函數體以及定義類所需的各種私有函數
  • 封裝
    • 實現類的接口和實現的分離
    • 影藏實現細節,用戶只能訪問接口無法訪問實現
  • 抽象數據類型
    • 類的設計者:考慮類的實現過程
    • 使用類的程序員:抽象思考類型做了什么,無須了解類型工作細節
7.1 定義抽象數據類型
  • Sales_item類 抽象數據類型 通過接口使用對象 不能訪問類數據成員
  • Sales_data類 不是抽象數據類型 允許用戶直接訪問數據成員->封裝(隱藏)數據成員 變成抽象數據類型
7.1.1 設計Sales_data類
  • 定義成員函數,先將其定義為普通函數,執行復合賦值運算
  • 用戶 不同語境決定了不同的含義
    • 用戶代碼或類的使用者 程序員
    • 應用程序使用者 如書店經理
    • 設計類接口時,應考慮使類易于使用
    • 使用類時,不應顧及類的實現機理
    • 開發應用程序,須充分了解用戶需求
    • 類設計者,應關注使用類的程序員的需求
    • 良好設計的類,直觀易于使用的接口,高效的實現過程
  • 使用改進的Sales_data類
7.1.2 定義改進的Sales_data類
  • 定義在類內部的函數隱式內聯inline
  • 定義成員函數
    • 所有成員須在類內部聲明,成員函數體可定義在類內或類外
  • 引入this
    • 調用成員函數,實際是在替某個對象調用它
    • 成員函數通過this隱式參數,訪問調用它的對象
    • 調用成員函數,用請求該函數的對象地址初始化this
    • 成員函數內部,可直接使用該對象成員,無須成員訪問運算符,對類成員的直接訪問看作this的隱式調用
    • 任何自定義名為this的參數或變量行為都是非法的
    • this總是指向調用該成員函數的對象,是一個常量指針,不允許改變this保存的地址
  • 引入const成員函數
    • const 修改隱式this指針的類型
    • 默認情況下,this指向類類型非常量版本的常量指針,意味著不能將this綁定到常量對象上,故不能在常量對象上調用普通成員函數
    • 無須修改數據成員時,將this設置為指向常量的指針有助于提高函數靈活性
    • 常量成員函數:
      • 將const關鍵字放在成員函數的參數列表后,表示this是一個指向常量的指針
      • 不能改變調用它的對象的內容,可以讀取數據成員,不能寫入新值
      • 常量對象/常量對象的引用或指針,都只能調用常量成員函數
  • 類作用域和成員函數
    • 類本身是一個作用域,類成員函數的定義嵌套在類的作用域內
    • 編譯器分兩步處理類
        1. 先編譯成員函數聲明
        1. 才輪到成員函數體
      • 故成員函數體可隨意使用類成員其他函數無須在意成員出現次序
    • 在類的外部定義成員函數
      • 定義必須與聲明匹配
        • 返回類型/形參列表/函數名都需與類內部聲明一致
      • 被聲明為常量成員函數,定義也須在參數列表后指定const屬性
      • 類外部定義的成員名字必須包含它所屬的類名
      • 使用作用域運算符::說明該函數被聲明在類內部,剩余代碼是位于內的作用域內的
    • 定義一個返回this對象的指針
      • 當定義函數類似于某個內置類型運算符時,應令該函數行為盡量模仿該運算符
      • 返回對象引用類型,需將調用函數對象當成一個整體訪問
        • return *this;解引用this指針以獲得執行該函數的對象
7.1.3 定義類相關的非成員函數
  • 定義輔助函數,概念上屬于類接口組成部分,實際上不屬于類本身
  • 非成員函數。通常將函數聲明和定義分離開來
  • 如果非成員函數是類的接口組成部分,函數聲明應與類在同一個頭文件內
  • 定義read和print函數
    • io類屬于不能被拷貝的類型,只能通過引用來傳遞他們
    • 讀取和寫入操作會改變流的內容,故兩函數都接受普通引用
  • 定義add函數
    • 默認情況下,拷貝類的對象拷貝的是對象的數據成員
7.1.4 構造函數
  • 構造函數:定義類對象被初始化的方式,控制對象初始化過程,初始化類對象數據成員
  • 只要類的對象被創建,就會執行構造函數
  • 構造函數名字與類名相同,沒有返回類型,也有一個參數列表和函數體
  • 類可包含多個構造函數,與其重載函數差不多,形參數量或類型須有區別
  • 構造函數不能被聲明為const。當創建類const對象時,直到構造函數完成初始化過程,對象才真正取得"常量"屬性。構造函數在const對象構造過程中可以向其寫值。
  • 合成的默認構造函數
    • 如果類沒有顯式定義構造函數,編譯器會隱式定義一個默認構造函數
    • 合成的默認構造函數初始化規則
      • 若存在類內初始值,用其來初始化成員
      • 否則默認初始化該成員
        • 默認初始化:定義時沒指定初值變量被默認初始化;內置類型定義于函數體外初始化為0,定義于函數體內則不被初始化。(建議初始化每一個內置類型變量)
  • 某些類不能依賴于合成的默認構造函數
    • 普通類必須定義自己的默認構造函數,原因有三
        1. 編譯器只會在我們沒有聲明任何構造函數時會隱式定義一個默認構造函數,一旦定義了其他構造函數,除非再定義一個默認構造函數,否則類沒有默認構造函數
        1. 合成的默認構造函數可能執行錯誤的操作。定義在塊中的內置類型(算術類型:字符 整型 浮點型 布爾型;空類型)/復合類型(數組和指針)的對象被默認初始化則他們的值是未定義的,同樣適用于默認初始化內置類型成員。(只有當類 內置/復合類型的成員全部都被賦予類內初始值時,該類才適用于合成的默認構造函數)
        1. 有時編譯器不能為某些類合成默認構造函數。(如:類中包含一個其他類類型成員且該成員類型沒有默認構造函數,編譯器將無法初始化該成員。)必須自定義默認構造函數,否則該類將沒有可用的默認構造函數。
  • 定義Sales_data的構造函數
  • =default的含義
    • ales_data()=default;一個不接受任何實參的默認構造函數
    • 定義目的:既需要其他形式的構造函數,也需要默認構造函數,希望該默認構造函數作用完全等同于合成默認構造函數
    • =default既可以和聲明一起出現在類的內部(內聯),也可以作為定義出現在類的外部
    • 若編譯器不支持類內初始值,默認構造函數應該使用構造函數初始值列表來初始化類的每個成員
  • 構造函數初始值列表
    • 負責為新創建的對象的一個或幾個數據成員賦值,如
Sales_data(const std::string &s):bookNo(s) {}
Sales_data(const std::string &s,unsigned n,double p):
           bookNo(s),uits_sold(n),revenue(p*n) {}
  • 當某個數據成員被構造函數初始值列表忽略時,它將以合成默認構造函數相同的方式隱式初始化(如使用類內初始值)
  • 若不能使用類內初始值,則所有構造函數都應該顯式地初始化每個內置類型的成員
  • 在類的外部定義構造函數
    • 構造函數無返回類型,定義從指定函數名開始,類外部定義構造函數,須指明構造函數是哪個類的成員
7.1.5 拷貝、賦值和析構
  • 拷貝:初始化變量以及以值的方式傳遞或返回一個對象
  • 賦值:使用賦值運算符
  • 銷毀:對象不存在時執行銷毀操作,局部對象會在創建它的塊結束時被銷毀,vector對象被銷毀時存儲在其中的對象也會被銷毀
  • 若不主動定義拷貝、賦值和析構操作,編譯器會替我們合成它們
  • 某些類不能依賴于合成的版本
    • 當類需要分配類對象之外的資源時(管理動態內存的類)
    • 使用vector或string類能避免分配和釋放內存帶來的復雜性,拷貝、賦值和析構的合成版本能正常工作。(對含vector成員的對象執行拷貝、賦值和析構時,會設法拷貝或賦值成員中的元素;對象被銷毀時,將銷毀vector對象,依次銷毀vector中的每一個元素)
    • 類中所分配的資源都應該直接以類的數據成員的形式存儲
7.2 訪問控制與封裝
  • 訪問說明符加強類的封裝性
    • public說明符后的成員在整個程序內都可以被訪問,public成員定義類的接口
    • private說明符之后的成員可以被類的成員函數訪問,但不能被使用該類的代碼訪問,private部分封裝(隱藏)類的實現過程
  • 再次定義Sales_data類
    • public接口部分:構造函數和部分成員函數
    • private實現部分:數據成員
  • 一個類可定義0/多個訪問說明符,每個說明符出現次數也沒有嚴格限定;每個說明符指定接下來的成員的訪問級別,有效范圍直到下一個訪問說明符或者到達類的結尾為止
  • 使用class或struct關鍵字
    • 唯一區別,class和struct的默認訪問權限不太一樣
    • struct:定義在第一個說明符之前的成員是public的
    • class:定義在第一個說明符之前的成員是private的
    • 出于統一編程風格:當定義的類的所有成員是public時,使用struct;當定義的類的所有成員是private時,使用class
7.2.1 友元
  • 類允許友元(其他類或者函數)訪問它的非公有成員,只需增加一條friend關鍵字開始的函數聲明
  • 友元聲明只能出現在類定義的內部,但出現位置不限;友元不是類的成員也不受所在區域訪問控制級別約束
  • 但一般最好在類定義開始或結束前的位置集中聲明友元
  • 封裝的益處
    • 確保用戶代碼不會無意間破環對象狀態
    • 數據成員定義為private的類作者可以較為自由地修改數據;只要類的接口不變,用戶代碼就無須改變
    • 將查錯限制在有限范圍內,極大降低維護代碼以及修成程序錯誤地難度
    • 當類的定義發生改變無須更改用戶代碼,但使用該類的源文件須重新編譯
  • 友元地聲明
    • 僅指定訪問權限,而非通常意義的函數聲明;類成員調用友元函數前須在友元聲明外再次聲明
    • 為使友元對類成員可見,通常將友元聲明與類本身放置在同一個頭文件中
    • 編譯器未強制限定友元函數須在使用之前在類的外部聲明;一些編譯器允許在尚無友元函數的初始聲明的情況下就調用它
7.3 類的其他特性
  • 類型成員、類的成員類內初始值、可變數據成員、內聯成員函數、從成員函數返回*this、如何定義類類型以及友元類
7.3.1 類成員再探
  • 定義一個類型成員
    • 自定義某種類型在類中的別名,與其他成員一樣存在訪問限制(public/private)
    • 用來定義類型的成員必須先定義后使用,因此類型成員通常出現在類開始的地方
  • Screen類的成員函數
  • 令成員作為內聯函數
    • 定義在類內部的成員函數自動inline
    • 可以在類內部作為聲明的一部分顯示聲明成員函數,也能在類的外部用inline關鍵字修飾函數的定義
    • 雖無須在聲明和定義同時說明inline但合法,最好只在類外部定義的地方說明inline使類更容易理解
    • 和在頭文件中定義inline函數原因一樣(編譯器想展開函數不僅需要函數聲明還需要函數定義,且多個定義須完全一致),inline成員函數也應該與相應的類定義在同一個頭文件中
  • 重載成員函數
    • 參數數量/類型上有所區別
  • 可變數據成員
    • 即使在const成員函數內也能修改某個數據成員,通過在變量聲明前加mutable關鍵字
    • 可變數據成員永遠也不會是const,即使它是const對象的成員(可用于記錄const成員函數被調用的次數)
  • 類數據成員的初始值
    • 類內初始值必須用=的初始化形式
    • 或花括號括起來的直接初始化形式
7.3.2 返回*this的成員函數
  • 定義返回為引用時返回對象本身而非對象副本,返回類型為非引用時返回*this的副本
  • 從const成員函數返回*this
    • 一個const成員函數如果以引用的形式返回*this,那么它的返回類型將是常量引用
  • 基于const的重載
    • 通過成員函數是否是const的可對其進行重載,原因與根據指針參數是否指向const而重載差不多(非常量版本函數對常量對象不可用,只能在常量對象上調用const成員函數;非常量對象可調用常量/非常量版本,但非常量版本是更好的匹配;根據對象是否是const決定了應該調用的函數版本)
    • 當一個成員調用另一個成員是,this指針在其中隱式傳遞
  • 對于公共代碼使用私有功能函數
    • 避免在多處使用同樣的代碼
    • 類規模發展,函數變得更復雜,將相同操作寫在一處較好
    • 可能在函數中添加某些調試信息,在一處添/刪更容易
    • 額外調用不增加開銷,因為在類內部定義,隱式地被聲明為內聯函數
7.3.3 類類型
  • 每個類定義唯一類型;兩個類即使成員(列表)完全一樣,兩個類也是不同的類型
  • 一個類的成員和其他任何類(或任何其他作用域)地成員都不是一回事
  • 可直接使用類名作為類型名,也可把類名跟在關鍵字class或struct后面
  • 類的聲明
    • 前向聲明:僅僅聲明類而暫時不定義它
    • 不完全類型:聲明之后定義之前(只能在非常有限的的情境下使用)
      • 可以定義指向這種類型的指針或引用
      • 也可以聲明(但不能定義)以不完全類型作為參數或者返回類型的函數
    • 創建類對象時該類必須被定義過,不能僅被聲明(編譯器無法了解對象所需儲存空間)
    • 類須先被定義才能用引用或指針訪問其成員(否則編譯器不清楚該類有哪些成員)
    • 直到類被定義后數據成員才能被聲明成這種類型,一個類成員的類型不能是類自己;但類允許包含指向它自身類型的引用或指針
7.3.4 友元再探
  • 可以將非成員函數/其他類/其他類已定義過的成員函數定義成友元
  • 友元函數能定義在類的內部 隱式內聯
  • 類之間的友元關系friend class Window_mgr;
    • 友元類的成員函數可以訪問此類包括非共有成員在內的所有成員
    • 友元關系不存在傳遞性,(即類A存在友元類B,類B存在友元類C,則類C不具有訪問類A特權)
    • 每個類負責控制自己的友元類或友元函數
  • 令成員函數作為友元
    • 當將成員函數聲明成友元時,須明確指出該成員函數屬于哪個類
    • 須仔細組織程序的結構以滿足聲明和定義的彼此依賴關系,設計程序的方式如下
      • 先定義類A,聲明a函數,但不能定義它;在a使用類B的成員之前必須先聲明類B
      • 接下來定義類B,包括對于a的友元聲明
      • 最后定義函數a,此時a才可以使用類B的成員
  • 函數重載和友元
    • 如想將一組重載函數聲明成友元,需對這組函數中的每一個分別聲明
  • 友元聲明和作用域
    • 友元聲明的作用是影響訪問權限,本身并非普通意義上的聲明
    • 就算在類的內部定義友元函數,也須在類的外部提供相應聲明使函數可見
    • 類的成員使用友元函數時,友元函數也須先被聲明過
    • 有的編譯器不強制執行上述關于友元的限定規則
7.4 類的作用域
  • 一個類就是一個作用域
  • 類的作用域之外,普通數據和函數成員只能由對象、引用或者指針使用成員訪問運算符訪問
  • 類類型成員則使用作用域訪問符訪問
  • 跟在類作用域運算符之后的名字都須是對應類的成員
  • 作用域和定義在類外部的成員
    • 一個類就是一個作用域,在類的外部定義成員函數時必須同時提供類名和函數名(類的外部,成員名字被隱藏)
    • 一旦遇到類名,定義剩余部分就在類的作用域之內了,包括參數列表和函數體(內可直接使用類的其他成員而無須再次授權)
    • 函數返回類型在函數名之前,當函數定義在類外部時,返回類型名字位于作用域之外,因此返回類型須指明它是哪個類的成員
7.4.1 名字查找與類的作用域
  • 名字查找
    • 在名字所在塊中尋找聲明語句,只考慮在名字試用前的聲明
    • 若沒找到,繼續查找外層作用域
    • 若最終沒找到匹配的聲明,程序報錯
  • 定義在類內部的成員
    • 編譯器先編譯成員的聲明
    • 直到類全部可見后才編譯函數體(處理完全部聲明后才會處理成員函數定義)
    • 所以定義在類內部的成員函數體能使用類定義中的任何名字
  • 用于類成員聲明的名字查找
    • 兩階段處理只適用于定義在類內的成員函數體中使用的名字
    • 聲明中使用的返回類型/參數列表的名字,都須在使用前確保可見
    • 若函數聲明使用了類中尚未出現的名字,則編譯器將在定義該類的作用域中繼續查找
  • 類型名要特殊處理
    • 內層作用域可以重新定義外層作用域中的名字
    • 但若成員使用了外層作用域中的類型名字,則類中不能在之后重新定義該名字
      • 重新定義類型名字是一種錯誤的行為
      • 類型名定義放在類開始處,能確保所有使用類型的成員都在類名定義后
  • 成員定義中的普通塊作用域的名字查找
    • 先在成員函數內查找名字聲明,在使用前的才有效
    • 成員函數內沒有,則在類內繼續查找,類的所有成員都可以被考慮
    • 類內也沒有該名字的聲明則在成員函數定義前的作用域內繼續查找
    • (不建議使用其他成員的名字作為某個成員函數的參數,成員函數參數會隱藏外層同名參數;但仍可通過加上類的名字或顯式使用this指針來強制訪問成員)
  • 類作用域之后,在外圍的作用域中查找
    • 編譯器在函數和類的作用域中都沒找到名字,將接著在外圍作用域中查找
    • 可顯式通過作用域運算符來進行請求外層作用域中的名字(::前什么都沒有表示全局作用域)
  • 在文件中名字的出現處對其進行解析
    • 當成員定義在類的外部時,不僅須考慮定義前的全局作用域中的聲明,還需考慮成員函數定義前的全局作用域中的聲明
7.5 構造函數再探 7.5.1 構造函數初始值列表
  • 定義變量時習慣立即對其進行初始化而非先定義再賦值
  • 若沒有在構造函數初始值列表中顯式初始化成員,則成員在構造函數體之前執行默認初始化
  • 使用構造函數初始值列表與在構造函數體內對數據成員執行賦值的效果相同。但深層次的影響完全依賴于數據成員的類型
  • 構造函數的初始值有時必不可少
    • 有時可忽略數據成員初始化與賦值之間的差異
    • 但若成員是const或引用則須將其初始化
    • 當成員屬于某種沒有定義默認構造函數的類的類型時也須初始化
    • (隨著函數體一開始執行,初始化就完成了,初始化const或引用類型數據成員的唯一機會就是構造函數初始值)
    • 很多類中 初始化(直接初始化數據成員)和賦值(先初始化再賦值)事關底層效率
    • 一些數據成員必須被初始化,養成使用構造函數初始值的習慣,能避免一些意想不到的編譯錯誤
  • 成員初始化的順序
    • 構造函數初始值中每個成員只能出現一次
    • 成員初始化順序與在類定義的出現順序一致,與初始值列表中的前后位置無關
    • 最好令構造函數初始值的順序與成員聲明的順序保持一致,盡量避免使用某些成員初始化其他成員,如可能最好使用構造函數參數作為成員初始值(可不必考慮成員初始化順序)
  • 默認實參和構造函數
    • 如果一個構造函數為所有參數都提供了默認實參,則實際上也定義了默認構造函數(因為可以不提供實參也能調用上述函數)
7.5.2 委托構造函數
  • 委托構造函數使用它所屬類的其他構造函數執行它自己的初始化過程(將自己的一些/全部職責委托給其他構造函數)
    • 也有一個成員初始值列表和函數體,成員初始值列表唯一入口是類名本身,參數列表須與類中另外一個構造函數匹配
    • 當一個構造函數委托另一個構造函數時,先執行受委托函數的初始值列表和函數體執行完后控制權才會交還給委托者的函數體
7.5.3 默認構造函數的作用
  • 當對象在默認初始化或者值初始化時自動執行默認構造函數
    • 默認初始化
      • 在塊作用域內不使用任何初始值定義一個非靜態變量/數組
      • 當一個類本身含有類類型成員且使用合成的默認構造函數時
      • 當類類型成員沒有在構造函數初始值列表中顯式初始化時
    • 值初始化
      • 數組初始化時提供初始值數量少于數組大小時
      • 當不使用初始值定義一個局部靜態變量時
      • 通過書寫形如T()(其中T為類型名稱)的表達式顯式請求值初始化時
    • 如果定義了其他構造函數,那么最好也提供一個默認構造函數
  • 使用默認構造函數
    • 如想定義一個使用默認構造函數進行值初始化的對象,正確方法是去掉對象名后的空括號(有空括號會當成一個不接受任何參數,返回值為類類型的函數)
7.5.4 隱式的類類型轉換
  • 轉換構造函數
    • 如果構造函數只接受一個實參,則實際上定義了轉換為此類類型的隱式轉換機制
    • 通過一個實參調用的構造函數定義了一條從構造函數的參數類型向類類型隱式轉換的規則
    • 編譯器用給定的參數自動創建一個(臨時)類對象(可以給常量引用的參數傳遞臨時量)
  • 只允許一步類類型轉換
    • 編譯器只會自動地執行一步類型轉換,當隱式使用兩種或以上轉換規則則是錯誤的
  • 類類型轉換不是總有效
    • 實際上構造了一個臨時對象,一旦操作完,隨后就將其丟棄不能夠再訪問了
  • 抑制構造函數定義的隱式轉換
    • 在要求隱式轉換的程序的上下文,可通過將構造函數聲明為explicit加以阻止隱式轉換
    • 關鍵字explicit只對一個實參的構造函數有效;
    • 需多個實參的構造函數不能用于執行隱式轉換,所以也無須指定為explicit
    • 只能在類內聲明構造函數時使用explicit關鍵字,在類外部定義時不應重復
  • explicit構造函數只能用于直接初始化
    • 不能將explicit構造函數用于拷貝形式的初始化過程
    • explicit關鍵字聲明構造函數時,只能以直接初始化的形式使用,編譯器將不會在自動轉換過程中使用該構造函數
  • 為轉換顯式地使用構造函數
    • 編譯器不會為explicit構造函數用于隱式轉換過程,但可以使用該構造函數顯式地強制進行類型轉換(也可利用static_cast使用explicit構造函數),創建的都是臨時類對象
  • 標準庫中含有顯式構造函數(單參數)的類
    • 接受一個單參數的const char*的string構造函數(不是explicit的)
    • 接受一個容器參數的vector構造函數(是explicit的)
7.5.5 聚合類
  • 聚合類 使用戶可以直接訪問其成員,具有特殊初始化語法形式
    • 所有成員都是public的
    • 沒有定義任何構造函數
    • 沒有類內初始值
    • 沒有基類,也沒有virtual函數
  • 可以提供一個花括號括起來的成員初始值列表,用它初始化聚合類的數據成員,初始值的順序必須與聲明的順序一致
    • 與初始化數組一樣,如果初始值列表中的元素個數少于類的成員數量,靠后的成員被值初始化;初始化列表的元素個數絕對不能超過類的成員數量
  • 顯式初始化類對象成員的三個明顯缺點
    • 要求類的所有成員都是public的
    • 將正確初始化類每個對象的重任交給了類的用戶,用戶易忘掉某個初始值或提供一個不恰當的初始值,初始化過程冗長乏味且容易出錯
    • 添加或刪除一個成員后,所有初始化語句都需更新
7.5.6 字面值常量類
  • constexpr函數的參數和返回值必須是字面值類型( 字面值類型:算術類型 引用 指針; 不屬于字面值類型: 某些自定義類 IO庫 string)
  • 字面值類型的類可能含有constexpr函數成員,該成員須符合constexpr函數的所有要求,是隱式const的
  • 數據成員都是字面值類型的聚合類是字面值常量類,若某類不是聚合類但符合以下要求,則也是字面值常量類
    • 數據成員都須是字面值類型
    • 類須至少含有一個constexpr構造函數
    • 若數據成員含有類內初始值,則內置類型成員的初始值必須是一條常量表達式;若成員屬于某種類類型,則初始值必須使用成員自己的constexpr構造函數
    • 類須使用析構函數的默認定義(負責銷毀類的對象)
  • constexpr構造函數
    • 構造函數不能是const的,但字面值常量類的構造函數可以是constexpr函數
    • constexpr構造函數可聲明成=default的形式或者刪除函數的形式;否則構造函數就須既符合構造函數要求(不能包含返回語句),又符合constexpr函數的要求(唯一可執行語句就是返回語句)->constexpr構造函數體一般是空的
    • 前置關鍵字constexpr就可以聲明一個constexpr構造函數
    • constexpr構造函數須初始化所有數據成員,初始值或者使用constexpr構造函數或者是一條常量表達式
    • constexpr構造函數用于生成constexpr對象以及constexpr函數函數的參數或返回類型
7.6 類的靜態成員
  • 有時類需要它的一些成員與類本身直接相關,而不是與類的各個對象保持關聯
  • 聲明靜態成員
    • 在類成員聲明前加static使其與類關聯在一起
    • 靜態成員可以是public或private的;靜態數據成員的類型可以是常量/引用/指針/類類型
    • 類靜態成員存在于任何對象之外,對象中不包含任何與靜態數據成員有關的數據。被所有類對象共享
    • 類靜態成員函數也不與任何對象綁定在一起,不包含this指針;靜態成員函數不能聲明成const的,也不能在static函數體內使用this指針(這限制適用于this的顯式使用,也對調用非靜態成員的隱式使用有效)
  • 使用類的靜態成員
    • 使用作用域運算符直接訪問靜態成員
    • 靜態成員雖不屬于類的某個對象,但仍可使用類對象、引用或指針來訪問靜態成員
    • 成員函數不用通過作用域運算符就能直接使用靜態成員
  • 定義靜態成員
    • 與其他成員函數一樣,既可以在類的內部也可以在類的外部定義靜態成員函數
    • 在類外部定義靜態成員時,不能重復static關鍵字,static值出現在類內部聲明語句
    • 指向類外部靜態成員時,須指明成員所屬類名
    • 靜態成員不屬于類的任何對象,它們不是在創建類的對象時被定義的,它們不由類的構造函數初始化;
    • 一般不能在類的內部初始化靜態成員,須在類的外部定義和初始化每個靜態成員,一個靜態數據成員只能定義一次
    • 類似全局變量,類靜態數據成員定義在任何函數之外;一旦被定義,就將一直存在于程序的整個生命周期中
    • 在類外部定義靜態數據成員,需指定對象類型名,類名、作用域運算符、成員自己的名字;從類名開始,定義語句的剩余部分都位于類的作用域之內,(可以訪問類的私有成員)
    • 為確保對象只定義一次,最好把靜態成員的定義與其他非內聯函數的定義放在同一個文件中
  • 靜態成員的類內初始化
    • 通常類靜態成員不應在類內部初始化,但可為靜態成員提供const整數型的類內初始值,不過要求靜態成員須是字面值常量類型的constexpr。初始值須是常量表達式,因成員本身就是常量表達式,所以可用于所有適合常量表達式的地方。(初始化了的靜態數據成員可用于指定數組維度)
    • 若靜態成員的應用場景僅限于編譯器可以替換它的值,則一個初始化的const或constexpr static不需要分別定義;若將它用于值不能替換的場景中,則該成員須有一條定義語句
    • 若在類的內部提供了一個初始值,則成員定義不能再指定一個初始值
    • 即使一個常量靜態數據成員在類內部被初始化了,通常也應在內的外部定義一下該成員
  • 靜態成員能用于某些場景,而普通成員不能
    • 靜態成員獨立于任何對象,某些非靜態數據成員可能非法的場合,靜態成員可以正常使用
    • 靜態數據成員可以是不完全類型(聲明之后定義之前)
    • 靜態數據成員的類型可以是它所屬類類型;非靜態數據成員則受到限制,只能聲明成它所屬類的指針或引用
    • 可以使用靜態數據成員作為默認實參,非靜態成員不能作為默認實參(值本身屬于對象一部分,無法真正提供一個對象以便從中獲取成員的值)
小結
  • 類 定義新類型 使程序更簡潔且易于修改
  • 類兩項基本能力
      1. 數據抽象 定義數據成員和成員函數的能力
      1. 封裝 保護類的成員不被隨意訪問的能力(private)
      • 類可將其他類或函數設為友元,使它們能訪問類非共有成員
  • 類可定義特殊成員:構造函數
    • 控制初始化對象的方式
    • 可以重載
    • 應使用構造函數初始值列表來初始化所有數據成員
  • 類可定義可變或靜態成員
    • 一個可變成員(mutable)永遠不會是const,在const函數內也能修改它的值
    • 靜態成員可以是函數或數據,存在于所有對象之外
術語表
  • 轉換構造函數:可用一個實參調用的非顯式構造函數(隱式將參數類型轉換為類類型)
  • 數據抽象:關注類型接口的編程技術;忽略類型實現細節只關注類型執行操作;數據抽象是面向對象編程和泛型編程基礎
  • 顯式構造函數:可以用一個單獨的實參調用但是不能用于隱式轉換的構造函數(構造函數聲明前加explicit)
  • 前向聲明:尚未定義名字前的聲明
  • 實現:類的成員(通常是私有的)定義了不希望使用類類型的代碼所使用的數據及任何操作
  • 不完全類型:已經聲明但是尚未定義的類型;不能用于定義變量或類的成員,但可用于定義指針或引用
  • 接口:類提供的(公有)操作

你是否還在尋找穩定的海外服務器提供商?創新互聯www.cdcxhl.cn海外機房具備T級流量清洗系統配攻擊溯源,準確流量調度確保服務器高可用性,企業級服務器適合批量采購,新人活動首月15元起,快前往官網查看詳情吧

分享文章:c++primer第7章類-創新互聯
網址分享:http://www.yijiale78.com/article28/deoecp.html

成都網站建設公司_創新互聯,為您提供App開發服務器托管網站導航品牌網站設計做網站虛擬主機

廣告

聲明:本網站發布的內容(圖片、視頻和文字)以用戶投稿、用戶轉載內容為主,如果涉及侵權請盡快告知,我們將會在第一時間刪除。文章觀點不代表本網站立場,如需處理請聯系客服。電話:028-86922220;郵箱:631063699@qq.com。內容未經允許不得轉載,或轉載時需注明來源: 創新互聯

h5響應式網站建設