簡體   English   中英

C ++類成員名稱查找問題(關於標准n3225的措辭)

[英]C++ class member name lookup issues (regarding the wording of standard n3225)

我對標准10.2 / 13感到非常困惑,

[注意:即使名稱查找的結果是明確的,使用在多個子對象中找到的名稱仍然可能是模棱兩可的(4.11、5.2.5、5.3.1、11.2)。

struct B1 {
  void f();
  static void f(int);
  int i;
};
struct B2 {
  void f(double);
};
struct I1: B1 { };
struct I2: B1 { };
struct D: I1, I2, B2 {
  using B1::f;
  using B2::f;
  void g() {
    f(); // Ambiguous conversion of this
    f(0); // Unambiguous (static)
    f(0.0); // Unambiguous (only one B2)
    int B1::* mpB1 = &D::i; // Unambiguous
    int D::* mpD = &D::i; // Ambiguous conversion
  }
};

我看不出為什么這是明確的int B1 :: * mpB1 =&D :: i; //明確

Visual C ++,Gcc和CLang都說這是對D :: i的模糊訪問!

該措辭似乎與核心問題#39 http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_defects.html#39有關 ,最終建議在此處: http:// www 。開-std.org / JTC1 / SC22 / WG21 /文檔/文件/ 2004 / n1626.pdf

我現在發現新的基於算法的措詞(10.2 / 3-10.2 / 6)更加令人困惑,因為10.2 / 9、10.2 / 10、10.2 / 11和10.2 / 13中的注釋均未完全符合10.2 / 3。 3-10.2 / 6。 我可以將10.2 / 9-10.2 / 11作為例外,但是我對10.2 / 13感到特別困惑。 我不知道13.2 / 13的意圖。

應該如何根據10.2 / 3-10.2 / 6查找10.2 / 13中的示例? 10.2 / 13的意圖是什么,即10.2 / 13被視為10.2 / 3-10.2 / 6的例外情況是什么?

請給我一些提示。 非常感謝你。


經過一番思考,我認為10.2 / 13的意圖更清晰了。

int B1 :: * mpB1 =&D :: i; //明確

這應該是明確的,當前的編譯器對此是錯誤的。 這是明確的,因為指向類成員初始化的指針尚不涉及訪問對象。

int D :: * mpD =&D :: i; //不明確的轉換

這實際上意味着從int B1 :: * mpB1轉換為int D :: * mpD時,由於基類模棱兩可,因此轉換模棱兩可。

對於B1 :: *情況,解釋是明確的,只是從B1的起始處到i的偏移量。

在5.3.1 / 3中:

struct A { int i; };
struct B : A { };
... &B::i ... // has type int A::*

因此,訣竅是首先使&D :: i的類型為B1 :: *。 然后:

int B1::* mpB1 = &D::i; // Unambiguous

很簡單。 然后產生了興趣:

int D::* mpD = &D::i; // Ambiguous conversion

在這里,RHS的類型為B1 :: *,並且需要進行轉換,因為我們需要確定要引用的是哪個鹼基。

這個:

int B1::* mpB1 = &D::i; // Unambiguous

這是明確的,因為結果已分配給pointer to member類B pointer to memberpointer to member
因此,選擇哪個i並不重要,因為偏移是相對於B成員(而不是父D類)而言的。

因此,對於您我來說,這是明確的,但我認為編譯器無法處理。

快速檢查ISO IEC 14882 2003第10節沒有此示例,也沒有類似的示例。 C ++ 0x是草案標准,而VC ++ / GCC / CLang不兼容。

我的猜測:這是新auto鍵入的一些副產品,在較舊的C ++標准中找不到。

FWIW,我正在復制我給這個問題的Usenet副本的答案:

大家好,

我對標准n3225 10.2 / 13感到非常困惑,
[注意:即使名稱查找的結果是明確的,使用在多個子對象中找到的名稱仍然可能是模棱兩可的(4.11、5.2.5、5.3.1、11.2)。

struct B1 {
  void f();
  static void f(int);
  int i;
};
struct B2 {
  void f(double);
};
struct I1: B1 { };
struct I2: B1 { };
struct D: I1, I2, B2 {
  using B1::f;
  using B2::f;
  void g() {
    f(); // Ambiguous conversion of this
    f(0); // Unambiguous (static)
    f(0.0); // Unambiguous (only one B2)
    int B1::* mpB1 = &D::i; // Unambiguous
    int D::* mpD = &D::i; // Ambiguous conversion
  }
};

我看不出為什么這是明確的int B1 :: * mpB1 =&D :: i; //明確

&D::i類型為int B1::* ,並且明確引用B1數據成員i 如果使用D對象取消引用或將其分配給int D::* ,則將根據需要獲得歧義。

Visual C ++,Gcc和CLang都說這是對D :: i的模糊訪問!

這些編譯器都沒有實現10.2。

該措辭似乎與核心問題#39 http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_defects.html#39有關 ,最終建議在此處: http:// www .open-std.org / jtc1 / sc22 / wg21 / docs / papers / 2004 / n1626.pdf我現在發現基於算法的新措詞(10.2 / 3-10.2 / 6)更加令人困惑,因為沒有注釋10.2 / 9、10.2 / 10、10.2 / 11和10.2 / 13中的數字完全符合10.2 / 3-10.2 / 6。 我可以將10.2 / 9-10.2 / 11作為例外,但是我對10.2 / 13感到特別困惑。 我不知道13.2 / 13的意圖。

您需要提供示例以說明您不了解的內容。

應該如何根據10.2 / 3-10.2 / 6查找10.2 / 13中的示例? 10.2 / 13的意圖是什么,即在什么情況下10.2 / 13被視為10.2 / 3-10.2 / 6的例外?

基於新算法的查找規則將運行時問題(查找唯一對象)與編譯時間/查找問題(查找名稱所引用的聲明)分離。

以下是采用新措辭的格式:

struct Z { int z; };
struct X : Z { };
struct Y : Z { };
struct A : X, Y { };

struct B : A {
  using A::z;
};

聲明using A::x; 在B中引入一個成員名稱,該成員名稱引用聲明Z::z 在聲明性上下文中,這完全可以。 僅當您作為成員訪問表達式(5.2.5)訪問B::z時,才會引發錯誤。

不要因為誤認為成員指針的情況而感到難過。 過去也這樣做 ,相應的問題報告實際上將其納入了C ++ 0x草案。 當他們發現更改錯誤時,他們幸運地將其更改回去

暫無
暫無

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

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