2012-10-09 40 views
5

Lo que solía tener:El uso de un MatrizParam, pero que requiere al menos un parámetro

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

El primero sólo llama a la segunda con {channel} para convertir su parámetro en una matriz.

Decidí que tener que crear una lista de canales para pasar al método era incómodo y elegí combinar las dos sobrecargas en un método que toma un ParamArray.

Public Sub Subscribe(ParamArray channels() As ChannelType) 

'Usage 
Subscribe(ChannelType.News) 
Subscribe(ChannelType.News, ChannelType.Sports) 
Subscribe() 'Oops... this is valid 

¿Qué es la "mejor práctica" aquí? Me gusta la flexibilidad que ParamArray me da para dejar pasar cosas, pero no ayuda al desarrollador a "fallar-más rápido" a través de los comentarios de errores del compilador ... eso significa que algo como un ArgumentException está fuera de cuestión aquí ya que las personas consumir este método puede no estar escribiendo pruebas unitarias. Una opción es la siguiente ...

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

pero me siento como que me pone cerca de volver al punto de partida, es confuso, y requiere mi aplicación de ese método a ser menos sencilla.

Respuesta

11

otra opción a considerar sería

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 

la etiqueta <Obsolete()> con un segundo parámetro de True informa al compilador que intentar utilizar el método de marcado debe r esult en un error de compilación. Dado que el método en cuestión se usaría cuando, y solo cuando, se intenta invocar el método sin ningún parámetro, causaría un error solo en esos momentos. Tenga en cuenta que no se usará el método si se intenta pasar el método a una matriz de cero elementos de Integer; en ese caso, se usaría la forma normal ParamArray.

+0

¡Eso es inteligente! –

+0

Creo que esta respuesta lo consigue ... lo siento @ Meta-Knight! Me gusta cómo obtengo los comentarios del compilador y obtengo una facilidad de uso simple con la posibilidad de simplemente iterar sobre el 'ParamArray' en lugar de tener que concaturar un solo elemento con' ParamArray' para iterar sobre mis argumentos. –

+2

@JeffBridgman: Tenga en cuenta que este código, a diferencia del enfoque con un argumento separado, permite que el código pase en una matriz que contiene todos los parámetros en lugar de tener que pasar el primer elemento y una matriz que contiene el resto; como consecuencia, aunque puede rechazar la invocación con una lista de argumentos vacía, no puede, en tiempo de compilación, rechazar la invocación con una matriz vacía. – supercat

6

Creo que la opción que mencionaste es la mejor opción. El uso de nombres más claras para sus parámetros hará que sea menos confuso:

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

La otra opción es hacerla cumplir en tiempo de ejecución, pero como usted ha dicho que no dejaría tan rápido:

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

¡Buena respuesta! Si tuviera un dominio de problemas donde había un canal primario y canales adicionales, ¡la primera opción que mencionó sería perfecta! –

Cuestiones relacionadas