2012-10-09 4 views
5

Was ich habe folgende Zwecke verwendet:ein ParamArray Verwendung, sondern erfordert mindestens einen Parameter

Public Sub Subscribe(channel As ChannelType) 
Public Sub Subscribe(channels As IEnumerable(Of ChannelType)) 

Die erste nennt man nur die zweite mit {channel} seine Parameter in ein Array zu konvertieren.

Ich entschied, dass das Erstellen einer Liste von Kanälen, die an die Methode übergeben werden, umständlich war und entschied, die beiden Überladungen in einer Methode zu kombinieren, die eine ParamArray dauert.

Was ist die "beste Praxis" hier? Ich mag die Flexibilität, die ParamArray gibt mir in nur Leute lassen Zeug übergeben, aber es hilft nicht, den Entwickler "fail-faster" über Compiler-Fehler-Feedback zu helfen ... das bedeutet, dass so etwas wie ein ArgumentException ist nicht in Frage, da Menschen Bei dieser Methode dürfen keine Komponententests geschrieben werden. Eine Option ist die folgende ...

Public Sub Subscribe(channel As ChannelType) 
Public Sub Subscribe(channel As ChannelType, ParamArray channels() As ChannelType) 

Aber ich fühle mich wie das bringt mich fast wieder auf Platz eins, ist verwirrend und erfordert meine Implementierung dieser Methode weniger als geradlinig.

Antwort

11

eine weitere Möglichkeit zu prüfen, wäre

Module ParamArrayTest 
    Sub ShowThings(ParamArray MyThings() As Integer) 
     For Each thing As Integer In MyThings 
      Debug.Print("{0}", thing) 
     Next 
    End Sub 

    ' Don't try to call without parameters: 
    <Obsolete("Must have at least one parameter", True)> Sub ShowThings() 
     Throw New ArgumentException("Must specify at least one parameter") 
    End Sub 

    Sub Test() 
     ShowThings(3, 4, 5) 
     ShowThings() 
    End Sub 
End Module 

der <Obsolete()>-Tag mit einem zweiten Parameter von True die Compiler darüber informiert, dass die markierte Methode zu verwenden versuchen sollte r Dies führt zu einem Kompilierungsfehler. Da die betreffende Methode nur dann verwendet würde, wenn versucht wird, die Methode ohne Parameter aufzurufen, würde sie nur zu solchen Zeiten einen Fehler verursachen. Beachten Sie, dass die Methode nicht verwendet wird, wenn versucht wird, die Methode an ein Null-Element-Array von Integer zu übergeben; In diesem Fall würde das normale Formular ParamArray verwendet werden.

+0

Das ist schlau! –

+0

Ich denke, diese Antwort bekommt es ... sorry @ Meta-Knight! Ich mag, wie ich Compilerfeedback bekomme, und ich bekomme die einfache Benutzerfreundlichkeit mit der Fähigkeit, einfach über das "ParamArray" iterieren zu können, anstatt ein einzelnes Element mit dem 'ParamArray' zu contrahieren, um über meine Argumente zu iterieren. –

+2

@ Jeff Bridgman: Beachten Sie, dass dieser Code im Gegensatz zu dem Ansatz mit einem separaten Argument Code in einem Array übergeben kann, das alle Parameter enthält, anstatt das erste Element und ein Array mit dem Rest übergeben zu müssen; Folglich kann der Aufruf mit einer leeren Argumentliste nicht zugelassen werden, während der Kompilierung kann er den Aufruf mit einem leeren Array nicht verbieten. – supercat

6

Ich denke, dass die Option, die Sie erwähnten, die beste Option ist. Mit klaren Namen für Ihre Parameter wird es weniger verwirrend:

Public Sub Subscribe(mainChannel As ChannelType, ParamArray otherChannels() As ChannelType) 

Die andere Option ist es zur Laufzeit zu erzwingen, aber wie Sie sagt, es würde nicht so schnell ausfallen:

Public Sub Subscribe(ParamArray channels() As ChannelType) 
    If channels.Count = 0 then 
     Throw new InvalidOperationException("At least one channel is needed") 
    End If 
End Sub 
+0

Gute Antwort! Wenn ich eine Problem-Domain hätte, wo es einen primären Kanal und zusätzliche Kanäle gäbe, wäre die erste Option, die du erwähnt hast, perfekt! –