Laden...

[erledigt] Methoden überladen mit Klasse als Parameter --> Polymorphie

Erstellt von Horsti vor 9 Jahren Letzter Beitrag vor 9 Jahren 3.738 Views
H
Horsti Themenstarter:in
5 Beiträge seit 2015
vor 9 Jahren
[erledigt] Methoden überladen mit Klasse als Parameter --> Polymorphie

Hallo,

im folgenden Code wird die Methode "void doIt(A a)" aufgerufen.
Warum nicht die Methode "void doIt(B b)"? Wie muss der Code
abgeändert werden, dass die Methode "void doIt(B b)" aufgerufen wird?

Die Methoden "void doIt(...)" sollen in der Klasse Program verbleiben
und NICHT in die Klassen A bzw. B verschoben werden.

Gruß
Horsti

 
using System;

namespace Ueberladen
{
    class A
    {
    }

    class B : A
    {
    }

    class Program
    {
        static void Main(string[] args)
        {
            Program program = new Program();

            A a = new B();
            program.doIt(a);
            Console.ReadKey();
            // --> A
        }

        void doIt(A a)
        {
            Console.WriteLine("A");
        }

        void doIt(B b)
        {
            Console.WriteLine("B");
        }
    }
}

189 Beiträge seit 2014
vor 9 Jahren

Hallo Horsti,
was du wahrscheinlich möchtest, ist statt

Programm program = new Program();
program.doIt(a);

den "this"-Operator zu verwenden:


this.doIt(a);
this.doIt(b);

Solange du auf die Methoden der Klasse "Program" zugreifen möchtest.
Siehe Namenskonflikte mit this lösen

J
251 Beiträge seit 2012
vor 9 Jahren

naja der "this"-Operrator ist nicht das Problem, wenn ich es verstanden habe.

Horsti hat 2 gleiche Methoden. Nun wird ein Objekt initialisiert vom Typ der Basisklasse.
Erwünscht ist aber nun der Methodenaufruf mit dem Parameter der vererbten Klasse.

189 Beiträge seit 2014
vor 9 Jahren

Ahh, stand aufm Schlauch ...
Du hälst zwar das Objekt in einer Variablen deines Basistyps, willst aber dann das Objekt in seinem eigentlichen Typ behandeln, richtig?
Naja, du betreibst ja eben Boxing.
Also musst du den Wert unboxen, also zurückcasten.

H
Horsti Themenstarter:in
5 Beiträge seit 2015
vor 9 Jahren

@Ezio: Der "this"-Operator löst das Problem nicht.

Soweit ich mich erinnern kann, würde in C++ die Methode "void doIt(B b)" aufgerufen...

Was auch interessant ist: Schon bei der statischen Codeanalyse wird die Methode
"void doIt(B b)" als nicht verwendet angezeigt...

189 Beiträge seit 2014
vor 9 Jahren

Ja und hast du auch meinen 2. Beitrag gelesen?
Boxing/Unboxing

H
523 Beiträge seit 2008
vor 9 Jahren

Du musst a in B konvertieren:


if (a is B)
{
    program.doIt((B)a);
}
else
{
    program.doIt(a);
}

H
Horsti Themenstarter:in
5 Beiträge seit 2015
vor 9 Jahren

Leider zu spät 😃

Aber zurückcasten möchte ich eigentlich nicht.
Das ist sehr unschön.
Eigentlich sollte das doch die Polymorphy erledigen.
So wie in C++.

709 Beiträge seit 2008
vor 9 Jahren

Dafür müsstest du doIt als virtual-Methode in A implementieren und diese dann in B überschreiben.

1.696 Beiträge seit 2006
vor 9 Jahren

Eigentlich sollte das doch die Polymorphy erledigen.
So wie in C++.

Schon, wenn du richtig implementiert, siehe Polymorphismn in C#

Ich bin verantwortlich für das, was ich sage, nicht für das, was du verstehst.

**:::

H
Horsti Themenstarter:in
5 Beiträge seit 2015
vor 9 Jahren

Die Methoden "void doIt(...)" sollen in der Klasse Program verbleiben
und NICHT in die Klassen A bzw. B verschoben werden.

Die Klassen A bzw. B sind reine Datenklassen. Diese sollen keine Funktionalität enthalten.

189 Beiträge seit 2014
vor 9 Jahren

Hallo Horsti,
wenn du unbedingt es nicht so machen möchtest, wie vbprogger es geschrieben hat, bleibt dir nur die Methode mit Boxing/Unboxing, also das was ich und hypersurf dir sagen wollten.

742 Beiträge seit 2005
vor 9 Jahren

Das nennt sich dynamische Bindung: Dynamische Bindung

Gibts es in C# allerdings nicht. Die einzige Möglichkeit: Selber implementieren.

H
Horsti Themenstarter:in
5 Beiträge seit 2015
vor 9 Jahren

@malignate: Danke "dynamische Bindung" war der entscheidende Hinweis.

Dynamische Bindung wurde mit C# 4.0 eingeführt.

Jetzt geht es:

dynamic a = new B();
            program.doIt(a);
            Console.ReadKey();
            // --> B

R
228 Beiträge seit 2013
vor 9 Jahren

Das nennt sich dynamische Bindung:
>

Gibts es in C# allerdings nicht. Die einzige Möglichkeit: Selber implementieren.

Ohne dynamisches Binden würde Polymorphie doch überhaupt nicht funktionieren oder vertue ich mich hier? Spätestens wenn du eine Methode in c# als virtual kennzeichnest wird sie mit in die Virtual function Table übernommen und so weiter.....

742 Beiträge seit 2005
vor 9 Jahren

Ja, du hast Recht, das war der falsche Link und der falsche Begriff. Habe Multimethoden gesucht:

Multimethode

oder auch:

http://blogs.msdn.com/b/laurionb/archive/2009/08/13/multimethods-in-c-4-0-with-dynamic.aspx