www.mikrocontroller.net

Forum: PC-Programmierung C# und ternärer Operator


Autor: Alex (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Warum funktioniert in C# ...

MyBaseClass foo(bool bar)
{
    if (bar) return new MyDerivedClass1();
    else return new MyDerivedClass2();
}

... aber nicht ...

MyBaseClass foo(bool bar)
{
    return bar ? new MyDerivedClass1() : new MyDerivedClass2();
}

... ???

Fehlermeldung:

Type of conditional expression cannot be determined because there is no 
implicit conversion between 'MyDerivedClass1' and 'MyDerivedClass2'

Gruß,
Alex

Autor: Klaus Wachtler (mfgkw)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Im ersten Fall muß nur bei jedem return zur Basisklasse gecastet werden,
das geht immer.

Im zweiten Fall dagegen weiß der Compiler noch nicht (bzw. weigert
sich, es zu sehen), daß letztlich etwas in der Basisklasse rauskommen
soll, während er über den Auswahloperator nachdenkt. Für den aber
müssen die beiden Operanden zueinander kompatibel sein, zwei
verschiedene Ableitungen einer Basisklasse sind das von sich aus
nicht. Erst das Ergebnis von ?: würde in die Basisklasse gecastet
werden wegen des return, aber da ist es schon zu spät.

Autor: Klugscheißer (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Versuch mal
return bar ? ( MyBaseClass)new MyDerivedClass1() : ( MyBaseClass)new 
MyDerivedClass2();

Autor: Markus (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
C# ist typstreng. Der Operator ?: hat genau einen Ergebnistyp. Welchen 
soll er denn in Deinem Fall nehmen? MyDerivedclass1, MyDerivedclass2 
oder MyBaseClass?

Wie Klugscheißer bereits geschrieben hat, kannst Du das Problem mit 
einem expliziten Type-Cast lösen. Oder aber Du machst, was der Compiler 
bemängelt: Implementiere doch einfach die impliziten Casts!
class MyDerivedClass1 {
    ...
    public static implicit operator MyBaseClass( MyDerivedClass1 val ) {
        return val; // ggf. (MyBaseClass)val
    }
    ...
}

class MyDerivedClass2 {
    ...
    public static implicit operator MyBaseClass( MyDerivedClass2 val ) {
        return val; // ggf. (MyBaseClass)val
    }
    ...
}

class MyBaseClass {
    ...
    public MyBaseClass Foo( MyDerivedClass1 o1, MyDerivedclass o2 ) {
        ...
        return ( cond ) ? o1 : o2;
    }
    ...
}

Gruß
Markus

Autor: Alex (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,

erstmal danke für die Infos!

@Markus
user-defined conversions to or from a base class are not allowed

Die Lösung mit dem Cast passt dafür. Im Prinzip sehe ich das 
Compilerverhalten an der Stelle aber als eher fragwürdig an. Für mich 
ist ein "?" nur die Kurzform von if-else, nicht mehr und nicht weniger 
...

Autor: Klaus Wachtler (mfgkw)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
das if-else ist nur eine stark vereinfachte Darstellung;
es gibt mehrere Unterschiede.

Autor: Arc Net (arc)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Alex schrieb:
> Hallo,
>
> erstmal danke für die Infos!
>
> @Markus
> user-defined conversions to or from a base class are not allowed
>
> Die Lösung mit dem Cast passt dafür. Im Prinzip sehe ich das
> Compilerverhalten an der Stelle aber als eher fragwürdig an. Für mich
> ist ein "?" nur die Kurzform von if-else, nicht mehr und nicht weniger
> ...

Vereinfacht gesagt:
? ist ein Ausdruck, der einen Wert zurückliefert
if ist kein Ausdruck, sondern eine Anweisung die keinen Wert 
zurückliefert (im Gegensatz z.B. zum if in Haskell, F#, Smalltalk etc)

Autor: Rolf Magnus (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
> Die Lösung mit dem Cast passt dafür. Im Prinzip sehe ich das
> Compilerverhalten an der Stelle aber als eher fragwürdig an.

Warum? Ich kenne C# nicht so, aber es ist wohl in der  Hinsicht wie C 
und C++, nämlich daß der Rückgabe-Typ eines Operators aussließlich von 
den übergebenen Argumenten abhängt und nicht davon, was man später mit 
dem zurückgegebenen Wert macht. Und in diesem Fall haben die beiden 
Argumente unterschiedlichen Typ, also müßte eins in den Typ des anderen 
konvertiert werden, was aber nicht geht, da keiner die Basisklasse vom 
anderen ist. Daß du nachher gern ein MyBaseClass hättest, ist dem 
Operator egal.

> Für michist ein "?" nur die Kurzform von if-else, nicht mehr und nicht
> weniger

Was es für dich ist, ist aber von relativ wenig Bedeutung.

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.