亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb

首頁 > 開發 > Java > 正文

Java、C++中子類對父類函數覆蓋的可訪問性縮小的區別介紹

2024-07-13 10:16:07
字體:
來源:轉載
供稿:網友

前言

“Java 和 C++ 中子類對父類函數覆蓋的可訪問性縮小的問題”的題目看起來比較學術化,但的確是一個容易忽視的問題。本文力求詳細闡述這一問題在 Java 以及 C++ 中的區別。

先介紹什么是“子類對父類函數覆蓋的可訪問性縮小”。對于繼承而言,子類可以覆蓋父類的“虛函數”——盡管 Java 中沒有虛函數這一術語,但可以把 Java 的所有函數都看作虛函數,因為 Java 的所有函數都可以被子類覆蓋。這里僅借用“虛函數”這一名詞的含義,不深究語言的細節。Java 和 C++ 都允許在覆蓋時,改變函數的可訪問性。所謂“可訪問性”,就是使用 public 、 protected 、 private 等訪問控制符進行修飾,用來控制函數能否被訪問到。通??稍L問性的順序為(由于 C++ 中沒有包的概念,因此暫不考慮包訪問控制符,這并不影響這里的討論):

public > protected > private

以 Java 為例:

class Base { protected void sayHello() {  System.out.println("Hello in Base"); }}class Child extends Base { public void sayHello() {  System.out.println("Hello in Child"); }}

注意:這里的 sayHello() 函數。父類 Base 中,該函數使用 protected 訪問控制符進行修飾。而子類將其改用 public ,這不會有任何問題。 子類對父類函數覆蓋時,擴大可訪問性,通常都不是問題。

當子類對父類函數覆蓋的可訪問性縮小時,Java 和 C++ 采取了不同的策略。

首先以 Java 為例,看下面的代碼:

class Base { public void sayHello() {  System.out.println("Hello in Base"); }}class Child extends Base { private void sayHello() {  System.out.println("Hello in Child"); }}

上面的代碼中,高亮的第 8 行會有編譯錯誤——這段代碼根本不能通過編譯! Java 不允許子類在覆蓋父類函數時,縮小可訪問性。 至于原因,我們可以用一個例子來說明。例如我們在類外部寫下面的代碼:

Base base = new Base();base.sayHello();base = new Child();base.sayHello();

假如之前的代碼可以通過編譯,那么就存在這么一種可能:當 base 指向 new Base() 時, sayHello() 是可以訪問到的,但是當 base 指向 new Child() 時, sayHello() 卻無法訪問到!在 Java 看來這是一個矛盾,應該避免出現這種問題,因此,Java 從編譯器的角度規定我們不能寫出上面的代碼。

針對 C++,情況又有所區別。來看 C++ 的例子:

class Base {public:  virtual void sayHello() {    std::cout << "Hello in Base";  }}class Child : public Base {private:  void sayHello() {    std::cout << "Hello in Child";  }}

這段代碼在 C++ 中是完全正確的。注意,這里的子類在覆蓋父類函數時, 縮小 了可訪問性。如果你沒有看出有什么問題,那么我們完全可以在類外部寫出下面的代碼:

Child child;child.sayHello(); // 不能通過編譯,因為 sayHello() 是 private 的static_cast<Base&>(child).sayHello(); // 可以通過編譯,因為 sayHello() 是 public 的

第 2 行調用是失敗的,因為在 Child 中, sayHello() 是 private 的,不能在外部調用。然而,當我們使用 static_cast 將 Child 強制轉換成 Base 對象時,事情發生了改變——對于 Base 而言, sayHello() 是 public 的,因此可以正常調用。

針對這一點,C++ 標準的 Member access control 一章中的 Access to virtual functions 一節可以找到如下的例子:

class B {public:  virtual int f();};class D : public B {private:  int f();};void f() {  D d;  B* pb = &d;  D* pd = &d;  pb->f(); // OK: B::f() is public, D::f() is invoked  pd->f(); // error: D::f() is private}

對此,C++ 標準給出的解釋是:

 Access is checked at the call point using the type of the expression used to denote the object for which the member function is called ( B* in the example above). The access of the member function in the class in which it was defined (D in the example above) is in general not known.

簡單翻譯過來有兩條要點:

  • 訪問控制是在調用時檢查的,也就是說,誰調用了這個函數,就檢查誰能不能訪問這個函數
  • 類中成員函數的可訪問性一般而言是不知道的,也就是說,檢查可訪問性時,并不能知道這個函數在定義時到底是 public 的還是 private 的,因此也就無法據此檢查可訪問性

正因如此,C++ 的調用方似乎可以通過一些技巧性轉換,“巧妙地”調用到原本無法訪問的函數。一個更加實際的例子是:Qt 里面, QObject::event() 函數是 public ,而其子類 QWidget 的 event() 函數則改變成 protected 。具體可以閱讀 Qt 的相關代碼。

總結來說,在子類覆蓋父類函數時,Java 嚴格限制了子類不能縮小函數可訪問性,但 C++ 無此限制。個人認為,從軟件工程的角度來說,Java 的規定無疑更具有工程上面的意義,函數的調用也更加一致。C++ 的標準則會明顯簡化編譯器實現,但是對工程而言并不算很好的參考。

PS:C++ 標準的正式版是需要購買的,但是草案可以免費下載。C++ 標準草案的下載地址可以在下面的頁面找到: https://isocpp.org/std/the-standard

總結

以上就是這篇文章的全部內容了,希望本文的內容對大家的學習或者工作具有一定的參考學習價值,如果有疑問大家可以留言交流,謝謝大家對VeVb武林網的支持。


注:相關教程知識閱讀請移步到JAVA教程頻道。
發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb
国产精品久久久久久久美男| 亚洲人精选亚洲人成在线| 欧美在线一区二区三区四| 成人精品久久av网站| 亚洲亚裔videos黑人hd| 国产精品18久久久久久首页狼| 成人做爰www免费看视频网站| 91精品国产高清久久久久久久久| 久久久这里只有精品视频| 国产欧美在线播放| 久久久久久久久久久久av| 美日韩精品视频免费看| 欧美午夜性色大片在线观看| 欧美超级免费视 在线| 久久久国产精品亚洲一区| 欧美电影免费在线观看| 国产欧美一区二区三区在线| 美女视频久久黄| 在线视频日本亚洲性| 欧美做爰性生交视频| 性色av一区二区三区在线观看| 国产成人综合精品| 日韩成人中文字幕在线观看| 国产一区二区三区视频免费| 欧美日本精品在线| 欧美自拍视频在线| 日韩免费不卡av| 欧美一级淫片播放口| 免费99精品国产自在在线| 日产日韩在线亚洲欧美| 欧美成人精品在线播放| 91精品国产91久久久久久| 福利一区福利二区微拍刺激| 欧美日本亚洲视频| 亚洲欧美另类中文字幕| 欧美性受xxxx黑人猛交| 亚洲色图国产精品| 欧美性生交xxxxxdddd| 成人在线视频网站| 精品综合久久久久久97| 国产在线一区二区三区| 亚洲性线免费观看视频成熟| 亚洲va久久久噜噜噜| 久久av中文字幕| 91视频免费网站| 欧美在线观看www| 久久精品国产久精国产思思| 欧美极品第一页| 国产精品极品美女粉嫩高清在线| 欧美在线视频a| 日韩成人在线免费观看| 国产91对白在线播放| 亚洲自拍在线观看| 欧美性xxxx| 国内精品400部情侣激情| 高清欧美性猛交| 久久精品久久久久久| 在线播放国产精品| 日韩欧美国产黄色| 亚洲跨种族黑人xxx| 亚洲综合大片69999| 2019国产精品自在线拍国产不卡| 欧美激情精品久久久久久大尺度| 高跟丝袜一区二区三区| 在线成人免费网站| 日韩最新在线视频| 国产自摸综合网| 国产精品极品美女在线观看免费| 中文字幕久久久| 狠狠躁18三区二区一区| 91精品久久久久久久久久| 日韩美女在线看| 欧美久久精品午夜青青大伊人| 亚洲视频第一页| 亚洲网在线观看| 国产精品久久国产精品99gif| 精品久久久久久久久久久久久久| 久久精品国产清自在天天线| 亚洲精品欧美极品| 亚洲三级黄色在线观看| 性欧美长视频免费观看不卡| 日韩精品在线播放| 97精品伊人久久久大香线蕉| 久久久久久91香蕉国产| 91九色国产在线| 91国内在线视频| 综合网中文字幕| 这里只有精品在线播放| 久久国产精品偷| 欧美日韩不卡合集视频| 18性欧美xxxⅹ性满足| 欧美精品生活片| 国产精品久久久久免费a∨| 69久久夜色精品国产7777| 国产成人精品久久亚洲高清不卡| 69视频在线播放| 北条麻妃一区二区在线观看| 欧美性xxxxxxx| 最新91在线视频| 91久久在线视频| 国产一区二区三区久久精品| 国产精品午夜视频| 国产一区二区三区在线| 日韩欧美一区二区三区| 2021久久精品国产99国产精品| 国产精品午夜国产小视频| 欧美大胆a视频| 精品国产自在精品国产浪潮| 欧美黑人一区二区三区| 日韩经典第一页| 麻豆国产va免费精品高清在线| 成人网页在线免费观看| 超碰精品一区二区三区乱码| 欧美激情欧美狂野欧美精品| 日韩免费av一区二区| 亚洲精品一二区| 亚洲精品98久久久久久中文字幕| 亚洲最新av在线| 美女久久久久久久| 国产日韩欧美日韩| 日韩av片永久免费网站| 国内成人精品一区| 日本韩国欧美精品大片卡二| 91在线精品播放| 亚洲第一精品久久忘忧草社区| www.精品av.com| 青青在线视频一区二区三区| 亚洲最新视频在线| 91色在线视频| 国模精品视频一区二区三区| 亚洲区bt下载| 色先锋久久影院av| 最近中文字幕2019免费| 亚洲精品久久久久久久久久久久| 欧美日韩国产一区在线| 欧美国产第二页| 亚洲国产另类 国产精品国产免费| 精品女同一区二区三区在线播放| 久热爱精品视频线路一| 久久亚洲一区二区三区四区五区高| 日本视频久久久| 欧美激情成人在线视频| 日韩综合视频在线观看| 欧美在线一区二区视频| www.国产精品一二区| 精品偷拍各种wc美女嘘嘘| 91日本在线视频| 久久久久久999| 日韩在线视频一区| 欧美激情一区二区三区高清视频| 最近2019好看的中文字幕免费| 日日摸夜夜添一区| 欧美性精品220| 全球成人中文在线| 亚洲国产黄色片| 97碰在线观看| 亚洲欧美成人在线| 久久久天堂国产精品女人| 亚洲一区二区福利| 精品人伦一区二区三区蜜桃网站| 成人福利网站在线观看| 日韩亚洲在线观看| 欧美精品电影在线| 欧美麻豆久久久久久中文|