Ausmischen und benannte Parameter in C#:Warum muss auch der Out-Parameter benannt werden?
-
13-12-2019 - |
Frage
Kurzfassung:Ein benanntes Argument, das einem folgt out
Das Argument gibt einen Compilerfehler aus, aber ich kann in der Sprachspezifikation keine Unterstützung für dieses Verhalten finden.
Lange Version:
Ich verwende das Enum.TryParse<TEnum>
Drei-Parameter-Überladung, aber ich würde es vorziehen, die zu benennen ignoreCase
Parameter, um meinen Code klarer zu machen, ein Aufruf wie:
MyEnum res;
b = Enum.TryParse<MyEnum>(inputString, true, out res);
lässt die Bedeutung des booleschen Werts unklar (es sei denn, diese Methode ist bekannt).1).Daher möchte ich Folgendes verwenden:
b = Enum.TryParse<MyEnum>(inputString, out res, ignoreCase: true);
Der Compiler meldet dies jedoch als Fehler:
Das benannte Argument „ignoreCase“ gibt einen Parameter an, für den bereits ein Positionsargument angegeben wurde
und die IDE hebt das hervor ignoreCase
Parameter.VS2010, das auf .NET 4 abzielt, und VS11 Beta, das entweder auf 4 oder 4.5 abzielt, liefern alle das gleiche Ergebnis.In allen Fällen ist die Benennung der out
Parameter beseitigt den Fehler.
b = Enum.TryParse<MyEnum>(inputString, result: out res, ignoreCase: true);
Ich habe dies mit verschiedenen Methoden ausprobiert (einschließlich der Vermeidung von Generika).2, sowohl aus dem Framework als auch in meiner Assembly:immer das gleiche Ergebnis:ein out
Parameter gefolgt von einem benannten Parameter führt zu einem Fehler.
Ich kann keinen Grund für diesen Fehler erkennen und §7.5.1 Argumentlisten des C#-Sprachspezifikation:Version 4.0 scheint keinen Grund zu liefern, warum ein out
gefolgt von einem benannten Parameter sollte einen Fehler ergeben.Der Text des Fehlers scheint eine Interpretation als Fehler zu unterstützen:Es gibt kein Positionsargument, für das eine gültige Übereinstimmung vorliegen könnte ignoreCase
.
Ist meine Interpretation der Spezifikation falsch?Oder ist das ein Compiler-Fehler?
C# 7.2-Update
Diese Einschränkung für alle benannten Argumente muss auf Positionsargumente folgen, als der Aufruf mit C# 7.2 aufgehoben wurde.
Sehen https://docs.microsoft.com/en-gb/dotnet/csharp/whats-new/csharp-7-2#non-trailing-named-arguments.
1 Daher der Ratschlag in den Framework Design Guidelines, den Sie bevorzugen sollten enum
Parameter.
2 Z.B:gegeben:
private static void TestMethod(int one, float two, out string three) {
three = "3333";
}
Dieser Aufruf gibt auch den gleichen Fehler für den benannten Parameter aus, es sei denn, der out
Parameter heißt auch:
TestMethod(1, out aString, two: 1.0f);
Lösung
Mit benannten Parametern können Sie Positionsargumente nicht „überspringen“.
Ihr Code wird so analysiert, dass er die ersten beiden Argumente übergibt:value
Und ignoreCase
, dann vorbei ignoreCase
wieder.
Es hat nichts damit zu tun out
ness des Parameters.
Sie können das Problem beheben, indem Sie auch den letzten Parameter wie benannt übergeben.
Andere Tipps
Jedes Positionsargument muss übereinstimmen. Wenn Sie mit der Neuordnung der Reihenfolge beginnen, indem Sie die Argumente benennen, müssen Sie alle Argumente neu anordnen, die auf das von Ihnen benannte Argument folgen.
Also diese Codezeile:
b = Enum.TryParse<MyEnum>(inputString, out res, ignoreCase: true);
Versucht zu passen out res
mit ignoreCase
, und dann benennen Sie diesen Parameter erneut, was den Compiler auslöst.Wahrscheinlich lauert hinter dem ersten ein weiterer Fehler out res
passt nicht dazu ignoreCase
.
Wenn Sie also „ignoreCase“ beim Umgang mit Positionsargumenten „überspringen“ möchten, müssen Sie das benennen out res
auch Argument.