Ich wollte eine Extension-Methode schreiben, die auf Wörterbüchern funktioniert, deren Werte eine Art Sequenz sind. Leider kann der Compiler die generischen Argumente aus meiner Verwendung der Methode nicht abzuleiten scheinen; Ich muss sie explizit angeben.
%Vor%Ich erkenne, dass Typinferenz keine exakte Wissenschaft ist, aber ich frage mich, ob es eine grundlegende "Regel" gibt, die ich hier vermisse - ich bin nicht vertraut mit den Details der Spezifikation.
Ich erkenne, dass Typschlussfolgerung keine exakte Wissenschaft ist
Ich bin mir nicht sicher, ob ich dem zustimme. Die Spezifikation ist ziemlich detailliert.
Ich habe mich gefragt, ob es eine grundlegende "Regel" gibt, die ich hier vermisse
Die grundlegende Regel, die Sie verpassen, ist wahrscheinlich, dass Einschränkungen nicht Teil der Signatur sind. Type Inference arbeitet von der Signatur ab.
Meiner Meinung nach gibt es gute Gründe für diese Designentscheidung. Viele Menschen glauben jedoch, dass ich moralisch falsch bin, wenn ich glaube, dass es gute Gründe für diese Designentscheidung gibt. Wenn Sie daran interessiert sind, zu lesen, was sich wie mehrere Millionen Wörter anfühlt, zu dem Thema, ob ich Recht oder Unrecht habe, finden Sie in meinem Artikel zu diesem Thema und den etwa hundert Kommentaren, dass ich falsch liege:
Ist das ein Nachteil des Inferenzprozesses?
Wohl, ja. Meiner Meinung nach ist es eine vernünftige Wahl angesichts konkurrierender Designanforderungen. (Diejenigen, die "tun, was der Benutzer gemeint hat" und "Fehler geben, wenn die Dinge mehrdeutig aussehen".)
ist meine Erwartung, dass der Compiler es in diesem Fall "nicht verstehen" sollte?
Nein. Du scheinst eine vernünftige Person zu sein, und deine Erwartung scheint auf einer guten Argumentation zu beruhen. Es ist jedoch durchaus möglich, eine vernünftige Erwartung zu haben, die dennoch nicht erfüllt ist. Dies wäre einer dieser Fälle.
Kann ich die Signatur der Methode so ändern, dass sie gleichermaßen funktionsfähig und dennoch "ableitbar" ist?
Das wird schwierig, da der generische Dictionary-Typ in seinen Konvertierungen nicht kovariant oder kontravariant ist. Das Konzept, das Sie erfassen möchten, kann im Typsystem nicht so einfach ausgedrückt werden, dass Schlussfolgerung möglich ist.
Wenn Sie es vorziehen, Sprachen mit einer fortgeschritteneren Typrückmeldung zu verwenden, sollten Sie F # verwenden. Wenn Sie Sprachen bevorzugen, die eher dazu neigen, "zu tun, was der Benutzer gemeint hat", als "Fehler bei Ambiguität zu melden", sollten Sie VB verwenden.
C # Typ-Inferenz funktioniert nicht von Constraints oder Rückgabewerten. Du wirst etwas mehr Glück mit
haben %Vor% Dies funktioniert, wenn Sie den Parameter als new Dictionary< string, IEnumerable<int>>()
deklarieren, aber nicht , wenn Sie ihn als new Dictionary<string, List<int>>()
deklarieren.
Ich muss sagen, dass ich in Abschnitt 7.5.2 von c # spec , es scheint, dass, da List<int>
IEnumerable<int>
implementiert, die Typrückkehr von TUnderlyingValue
funktionieren sollte. Dieser Abschnitt ist jedoch nicht einfach zu verstehen. Ich nehme an, es funktioniert nicht durch die mehreren "Ebenen", da SomeMethod<T>(IEnumberable<T> val){}
einfach funktionieren würde, indem es mit SomeMethod(new List<string>())
aufgerufen wird. In der Spezifikation, die sich auf die Auflösung eines Typs bezieht, in dem U = Ca<Va, Cb<Vb>>
enthalten ist, sehe ich nichts Genaues, also ist vielleicht Schlussfolgerung auf dieser Ebene nicht definiert.
Tags und Links c# generics type-inference