基本クラスオブジェクトa1
は、メモリ内の派生オブジェクトを指しています。したがってa1.Print()
はメソッド参照、つまりB().Print()
を呼び出しますが、このA().i
を使用してB().i
にアクセスすることはできません。
あなたはそれをキャストする必要があります。
Console.WriteLine(((B)a1).i);
あなたは同じ変数名を使用するので、あなたが混乱しています。これを試してみてください:このようなbi
にアクセスしようとし
class A
{
public int ai = 1;
public virtual void Print()
{
Console.WriteLine("I am A");
}
}
class B : A
{
public int bi = 2;
public override void Print()
{
bi++;
Console.WriteLine("I am B");
}
}
static void Main(string[] args)
{
A a1 = new B();
a1.Print();
Console.WriteLine(a1.ai);
Console.WriteLine(((B)a1).bi);
Console.Read();
}
はあなたのコンパイル時のエラーを与える必要があります。
Console.WriteLine(a1.bi); //ERROR: 'A' does not contain a definition for 'bi'...
更新:
解答へ追加する - などの実装これは、ベースクラスのメンバ変数の動作をオーバーライドすることもできます:
class A
{
private int i = 1;
public virtual int I
{
get { return i; }
}
public virtual void Print()
{
Console.WriteLine("I am A");
}
}
class B : A
{
private int i = 2;
public override int I
{
get { return i; }
}
public override void Print()
{
i++;
Console.WriteLine("I am B");
}
}
A a1 = new B();
a1.Print();
Console.WriteLine(a1.I);
Console.WriteLine(((B)a1).I);
出力:サディクが言ったことに加えて
I am B
3
3
基本クラスのメンバA()。iを隠すように、わかりやすく説明してください。 –
B.iはA.iとは無関係の新しい変数です。ちょうど同じ名前を持つことになります(名前を変更することでうまく対応しています)。 –
@ PetA。シュナイダー - 私はそれを考えました、実際には単純ではありません。名前が同じであるために問題が発生しなかったが、問題は、 'A 'によって提供されたインタフェースがコンパイル時に' B'の項目にアクセスできないということである。 OPの前提は、同じ変数名を持つと、派生したオブジェクトの変数へのアクセスが可能になるということでした。これは必ずしも変数名とは関係ありません。 – Sadique