簡體   English   中英

函數覆蓋不同的返回類型

[英]function overriding with different return types

返回類型是否會影響函數覆蓋? (據我所知,返回typde不是函數/方法簽名的一部分)在基類中,我有一個函數,它不獲取參數,返回int並且是純虛擬的。 在每個派生類中,我為返回類型定義了一個枚舉。在派生類中重寫了該函數,即它具有相同的簽名但行為不同。 問題是:覆蓋和返回類型的合法性是不是函數覆蓋的一部分嗎?

代碼示例:

class Base
{
  public:
  typedef int ret;
  virtual ret method() = 0;
};

class Der1
{
public:
  enum ret1{
    ret1_0,
    ret1_1
  };
  ret1 method() { return ret1_1;}
};

class Der1
{
public:
  enum ret2{
    ret2_0,
    ret2_1
  };
  ret1 method() { return ret2_0;}
};

您可以使用不同的返回類型覆蓋函數,但只允許使用協變返回類型

函數重寫意味着將在運行時調用Base類方法或Derived類方法,具體取決於指針指向的實際對象。
它意味着:
ie:可以通過調用Derived類方法替換可以調用Base類方法的每個地方,而無需更改調用代碼。

為了實現這一點,唯一可能的方法是限制重寫虛方法的返回類型以返回與Base類相同的類型或從該類派生的類型(共變量返回類型),因此Standard強制執行此條件。

如果沒有這個條件,現有代碼將通過添加新功能(新的重寫功能)而中斷。

簡短的回答:不,這是不允許或更好的,它不是覆蓋,而是覆蓋 ,即你不是重寫Base::method()而是創建一個具有相同名稱的新方法。 大多數編譯器會警告你。 使用您的示例代碼,但假設Base::method 不是純虛擬的,請考慮以下事項:

void callMethod(Base const& b)
{
  auto a1 = b.method();  //what should the type of a1 be? -> it's int. Every time.
  std::cout << a1 << '\n';
}

int main()
{
  Der1 d1;
  auto a2 = d1.method(); //a2 is ret1_1 of type ret1
  callMethod(d1);        //calls Base::method and prints that int, not Der1::method
}

你是對的,返回類型不是函數簽名的一部分。 但是當覆蓋虛函數時,簽名並不重要。 §10.3,7明確指出:

重寫函數的返回類型應與重寫函數的返回類型相同,或者與函數類的協變相同。 如果函數D::f覆蓋函數B::f ,則函數的返回類型如果滿足以下條件則是協變的:

- 兩者都是指向類的指針,都是對類的左值引用,或者兩者都是對類的右值引用

- 返回類型B::f中的類與D::f的返回類型中的類相同,或者是D::f類的返回類型中類的明確且可訪問的直接或間接基類D::f

- 指針或引用都具有相同的cv限定,並且返回類型D::f中的類類型具有與B::f的返回類型中的類類型相同的cv-qualification或更少的cv-qualification。

你有什么不是覆蓋。

c ++支持原始指針和原始引用的協變返回類型。

但就是這樣。

我們不應該通過覆蓋它來改變基類中函數的返回類型。 不建議通過隱藏基本成員來改變返回類型,因為它會導致一些不能以多態方式使用的奇怪的東西。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM