Esta es una pregunta bastante frecuente. Para más detalles, consulte la sección 7.4.1 y 7.4.3.1 de la especificación.
En pocas palabras: un método con una matriz params es aplicable ya sea en su "forma normal" o su "forma expandida". Es decir, se puede decir
PrintLength(new string[] {"hello"}); // normal form
PrintLength("hello"); // expanded form, translated into normal form by compiler.
Cuando se le dé una llamada que es aplicable en ambas formas , el compilador siempre elige la forma normal sobre la forma expandida.
Supongamos que elegimos la forma expandida cada vez que ambas aplicaban. Supongamos que tiene
void M(params object[] x) {}
¿Cómo pasaría una matriz nula a esto si siempre elegimos la forma expandida? Eso sería imposible!
Supongamos que usted ha dicho
M(new object[] { "hello" });
y siempre eligió la forma expandida. ¿Qué haría esto? Bueno, una matriz de objetos es un objeto, por lo que elegiría la forma expandida: haría otra matriz, envuelva esto en la matriz y pase eso.
La elección de la forma expandida sobre la forma normal conduce a resultados disparatados. Siempre es más sensato elegir la forma normal sobre la forma expandida.
¡Buena información! –
Buen post Eric. Podría agregar que con el primer PrintLength (null), está pasando un valor nulo a la función, mientras que con el segundo ejemplo PrintLength (s) está pasando un puntero de cadena (referencia) que en realidad no hace referencia a nada. Sin embargo, la referencia todavía existe en la memoria con un valor de 0 ya que es un puntero nulo. – regex
Estaba 90% seguro de que este era el caso, pero ese 10% simplemente seguía fastidiándome. – ChaosPandion