4

仮想メソッドを持つ基本クラスと、そのメソッドをオーバーライドする複数のサブクラスがあります。

これらのサブクラスの1つに遭遇したとき、オーバーライドされたメソッドを呼び出したいのですが、サブクラスの知識がありません。これを行うための醜い方法(値をチェックしてキャストする)を考えることはできますが、言語で行う方法があるはずです。リストに同じリスト内に複数のサブクラスを含めたいのですが、そうでなければ、明らかにリストを作成することができます。

編集:間違っていたコードのコメントを修正しました。これは、私が得た非常に適切な最初の答えにつながりました:)

例えば:

Class Foo 
{
    public virtual printMe()
    {
        Console.Writeline("FOO");
    }
}

Class Bar : Foo 
{
    public override printMe()
    {
        Console.Writeline("BAR");
    }
}

List<Foo> list = new List<Foo>();
// then populate this list with various 'Bar' and other overriden Foos

foreach (Foo foo in list) 
{
    foo.printMe(); // prints FOO.. Would like it to print BAR
} 
4

5 に答える 5

9
class Foo 
{
    public virtual void virtualPrintMe()
    {
        nonVirtualPrintMe();
    }

    public void nonVirtualPrintMe()
    {
        Console.Writeline("FOO");
    }
}

class Bar : Foo 
{
    public override void virtualPrintMe()
    {
        Console.Writeline("BAR");
    }
}

List<Foo> list = new List<Foo>();
// then populate this list with various 'Bar' and other overriden Foos

foreach (Foo foo in list) 
{
    foo.virtualPrintMe(); // prints BAR or FOO
    foo.nonVirtualPrintMe(); // always prints FOO
}
于 2008-12-23T23:18:56.517 に答える
1

なぜ「Foo」と印刷する必要があるのですか?それは仮想メソッドの目的ではありません。重要なのは、派生クラスは、インターフェースを変更せずに関数の動作方法を変更できるということです。Fooオブジェクトは「Foo」を印刷し、Barオブジェクトは「Bar」を印刷します。他の何かが間違っているでしょう。

于 2008-12-23T23:15:09.880 に答える
0

基本クラスから継承されたメンバーを明示的に非表示にするには、 new修飾子を使用します。継承されたメンバーを非表示にするには、同じ名前を使用して派生クラスで宣言し、new 修飾子で変更します。これにより、まさに必要な動作が得られます。

詳細については、http: //geekswithblogs.net/Mohamed/articles/28613.aspxをご覧ください。

于 2008-12-23T23:18:01.463 に答える
0

この状況で必要な動作を得るには、基本クラスで仮想を削除し、サブクラスで new を使用できます。

しかし、エド・スワングレンが指摘したように、なぜあなたはそうするのですか?

于 2008-12-23T23:19:59.963 に答える
0

呼び出したいオブジェクトを他のオブジェクトにキャストするだけの解決策はありませんか:

 foo.printMe(); // prints FOO.. Would like it to print BAR

になる

(Foo)foo.printMe(); // foo can be any derived class of Foo.

または、質問の一部が欠けていますか?

于 2008-12-23T23:31:42.153 に答える