Ich habe gelesen, dass .NET die Rückgabe von Referenzen unterstützt, C # jedoch nicht. Gibt es einen besonderen Grund? Warum ich so etwas nicht machen kann:
static ref int Max(ref int x, ref int y)
{
if (x > y)
return ref x;
else
return ref y;
}
c#
.net
reference
return-type
Tom Sarduy
quelle
quelle
return ref x
C# 7
:)Antworten:
Diese Frage war das Thema meines Blogs am 23. Juni 2011 . Danke für die tolle Frage!
Das C # -Team erwägt dies für C # 7. Weitere Informationen finden Sie unter https://github.com/dotnet/roslyn/issues/5233 .
UPDATE: Die Funktion hat es in C # 7 geschafft!
Du hast Recht; .NET unterstützt Methoden, die verwaltete Verweise auf Variablen zurückgeben. .NET unterstützt auch lokale Variablen , die verwaltete Verweise auf andere Variablen enthalten. (Beachten Sie jedoch, dass .NET keine Felder oder Arrays unterstützt , die verwaltete Verweise auf andere Variablen enthalten, da dies die Garbage Collection-Story übermäßig kompliziert. Auch die Typen "verwalteter Verweis auf Variablen" sind nicht in Objekte konvertiert werden und werden daher möglicherweise nicht als verwendet Typargumente für generische Typen oder Methoden.)
Der Kommentator "RPM1984" bat aus irgendeinem Grund um ein Zitat für diese Tatsache. RPM1984 Ich empfehle Ihnen, die CLI-Spezifikation Partition I Abschnitt 8.2.1.1, "Verwaltete Zeiger und verwandte Typen" zu lesen, um Informationen zu dieser Funktion von .NET zu erhalten.
Es ist durchaus möglich, eine Version von C # zu erstellen, die beide Funktionen unterstützt. Sie könnten dann Dinge wie tun
und dann nenne es mit
Ich weiß empirisch, dass es möglich ist, eine Version von C # zu erstellen, die diese Funktionen unterstützt weil ich dies getan habe . Fortgeschrittene Programmierer, insbesondere Leute, die nicht verwalteten C ++ - Code portieren, fragen uns oft nach mehr C ++ - ähnlichen Möglichkeiten, Dinge mit Referenzen zu tun, ohne den großen Hammer herausholen zu müssen, Zeiger zu verwenden und Speicher überall festzunageln. Durch die Verwendung verwalteter Referenzen erhalten Sie diese Vorteile, ohne die Kosten für die Leistungssteigerung Ihrer Speicherbereinigung zu bezahlen.
Wir haben diese Funktion in Betracht gezogen und tatsächlich genug implementiert, um sie anderen internen Teams zu zeigen, um deren Feedback zu erhalten. Aufgrund unserer Untersuchungen glauben wir jedoch, dass das Feature derzeit nicht breit genug ansprechend oder überzeugend ist, um es zu einem wirklich unterstützten Sprachfeature zu machen . Wir haben andere höhere Prioritäten und einen begrenzten Zeit- und Arbeitsaufwand zur Verfügung, daher werden wir diese Funktion in Kürze nicht mehr ausführen.
Um es richtig zu machen, müssten einige Änderungen an der CLR vorgenommen werden. Derzeit behandelt die CLR Rückgabemethoden als legal, aber nicht überprüfbar, da wir keinen Detektor haben, der diese Situation erkennt:
M3 gibt den Inhalt der lokalen Variablen von M2 zurück, aber die Lebensdauer dieser Variablen ist abgelaufen! Es ist möglich, einen Detektor zu schreiben, der die Verwendung von Ref-Returns bestimmt, die die Stapelsicherheit eindeutig nicht verletzen. Wir würden einen solchen Detektor schreiben, und wenn der Detektor die Stapelsicherheit nicht nachweisen könnte, würden wir die Verwendung von Ref-Rückgaben in diesem Teil des Programms nicht zulassen. Es ist keine große Menge an Entwicklungsarbeit, aber es ist eine große Belastung für die Testteams, sicherzustellen, dass wir wirklich alle Fälle haben. Es ist nur eine andere Sache, die die Kosten der Funktion so weit erhöht, dass die Vorteile derzeit die Kosten nicht überwiegen.
Wenn Sie mir beschreiben können, warum Sie diese Funktion wünschen, würde ich das sehr begrüßen . Je mehr Informationen wir von echten Kunden darüber haben, warum sie es wollen, desto wahrscheinlicher wird es eines Tages in das Produkt gelangen. Es ist ein süßes kleines Feature und ich würde es gerne irgendwie zu Kunden bringen können, wenn es genügend Interesse gibt.
(Siehe auch verwandte Fragen. Ist es möglich, eine Referenz auf eine Variable in C # zurückzugeben? Und kann ich eine Referenz in einer C # -Funktion wie C ++ verwenden? )
quelle
y
Leben zu bleibenM2
? Ich würde erwarten, dass diese Funktion wie Lambdas funktioniert, die Einheimische erfassen. Oder ist das von Ihnen vorgeschlagene Verhalten so, wie CLR mit diesem Szenario umgeht?Sie sprechen von Methoden, die einen Verweis auf einen Werttyp zurückgeben. Das einzige in C # integrierte Beispiel, das mir bekannt ist, ist der Array-Accessor eines Werttyps:
und jetzt erstellen Sie ein Array dieser Struktur:
In diesem Fall
points[0]
gibt der Array- Indexer einen Verweis auf struct zurück. Es ist unmöglich, einen eigenen Indexer zu schreiben (z. B. für eine benutzerdefinierte Sammlung), der dasselbe Verhalten wie "Referenz zurückgeben" aufweist.Ich habe die C # -Sprache nicht entworfen, daher kenne ich nicht alle Gründe dafür, sie nicht zu unterstützen, aber ich denke, die kurze Antwort könnte lauten: Wir können ohne sie gut miteinander auskommen.
quelle
Sie könnten immer so etwas tun wie:
quelle
C # 7.0 unterstützt die Rückgabe von Referenzen. Siehe meine Antwort hier .
quelle