2017-07-01 15 views
0

ベースがアクセスできない場合、基本クラス(またはその参照)へのユーザー定義変換を許可しないのはなぜですか?またはprivateアクセスできない基本クラスへのユーザー定義の変換演算子

クラスDそのpublicベースBあり、クラスDのオブジェクトにBB&又はB&&、おそらくはCV修飾)への参照を結合する暗黙のルールので、ユーザ定義の変換にありますB&は意味をなさない。しかし、基本クラスがprotectedまたはprivateの場合、暗黙ルールはもはや適用されません。では、なぜユーザー定義の変換をB&(またはconst B&またはB&&など)に使用することを許可しないのですか?

+2

変換の例を挙げても構いませんが、禁止されていますか? – dasblinkenlight

+2

あなたが何を求めているかは非常に不明です。問題を示す例、[mcve]を提供してください。 – Rakete1111

+0

@dasblinkenlightこれは禁止されていませんが、現在のルールのためにコンパイラによって考慮されていません。 –

答えて

1

標準ではこれを禁止していません。しかし、そのような変換演算子は決して使用されないと述べています。 [class.conv.fct]/1

変換関数は、(恐らくCV修飾を、(おそらくCV修飾)同じオブジェクトタイプ(又はそれへの参照)に(おそらくCV修飾)オブジェクトを変換するために使用されることはありません)基本クラス(またはそれへの参照)、または(場合によってはcv修飾された)voidになります。

オーバーロードの解像度は常に変換演算子よりも基本クラスのコンストラクタを優先し、変換演算子は決して呼び出されないため、暗黙の変換では不要です。アクセスチェックは常に過負荷解決後に行われるため、変換演算子は決して考慮されません。 (1)について

struct B { 
    B() = default; 
    B(const B&) = default; 
    B& operator=(const B&) = default; 
}; 

struct D : protected B { 
    operator B() { return *this; } 
}; 

int main() { 
    D d; 
    B b = d; // (1) 
    b = d; // (2) 
} 

、コピーコンストラクタB(const B&)は、コンストラクタが選択されるように、その後、変換演算子([over.match.ctor]/1)を用いBD変換よりよい一致です。しかし、現在はアクセスがチェックされており、Bのコピーコンストラクタはprotectedであるため、コンパイルされません。

(2)はほぼ同じものです。 B& operator=(const B&)は、ユーザ定義の変換演算子をDと呼び出すよりも、より良い一致であるため、オーバーロードの分解能によって選択されます。しかし、今度はBの代入演算子はprotectedなので、Dの外部にはアクセスできず、コードはコンパイルされません。

これは、唯一の理由がわかっている限り、オーバーロードの解像度がどのように機能するかです。

+0

「標準ではこれは禁止されていません」とは、「許可されていない」を「未使用」と読むことができます。それは文言のちょうど不正確です。 –

関連する問題