2009-07-31 18 views
7

Muy a menudo sucede que tengo métodos privados que se vuelven muy grandes y contienen tareas repetitivas, pero estas tareas son tan específicas que no tiene sentido ponerlas a disposición de cualquier otra parte del código.C#: ¿Por qué no podemos tener métodos internos/funciones locales?

Así que sería genial poder crear 'métodos internos' en este caso.

¿Existe alguna limitación técnica (o incluso filosófica?) Que impida que C# nos dé esto? ¿O me perdí algo?

Actualización de 2016: Esto viene y se llama 'función local'. Ver respuesta marcada.

+0

¿Qué hay más interno que un método privado? ¿Métodos solo disponibles para un método? Eso solo parece más código que menos. – kenny

+1

Te perdiste algo. C# ha tenido esta característica desde C# 2.0. –

+0

@Eric Lippert: ¿Pueden darnos algunos detalles? Gracias. – Marc

Respuesta

0

parece que vamos a conseguir exactamente lo que quería con funciones locales en C# 7/Visual Studio 15:
https://github.com/dotnet/roslyn/issues/2930

private int SomeMethodExposedToObjectMembers(int input) 
{ 
    int InnerMethod(bool b) 
    { 
     // TODO: Change return based on parameter b 
     return 0; 
    } 

    var calculation = 0; 
    // TODO: Some calculations based on input, store result in calculation 

    if (calculation > 0) return InnerMethod(true); 
    return InnerMethod(false); 
} 

Demasiado malo que tuve que esperar más de 7 años para esto :-)

Consulte también otras respuestas para versiones anteriores de C#.

14

Bueno, podemos tener "métodos anónimos" definidos dentro de una función (no sugerir el uso de ellos para organizar un método grande):

void test() { 
    Action t =() => Console.WriteLine("hello world"); // C# 3.0+ 
    // Action t = delegate { Console.WriteLine("hello world"); }; // C# 2.0+ 
    t(); 
} 
+0

+1, esto es exactamente lo que quiere. – Blindy

+0

@Mehrdad Afshari: Parece interesante, parece que "Func" podría usarse para esto. ¿Pero por qué no los usarías para organizar un método grande? – Marc

+0

@Marc: Debería considerar desglosar un método grande en varios métodos más pequeños, no en métodos anónimos. –

7

Si algo es largo y complicado que por lo general es bueno practique para refactorizarlo a una clase separada (ya sea normal o estática, dependiendo del contexto); allí puede tener métodos privados que serán específicos solo para esta funcionalidad.

2

Sé que a muchas personas no les gustan las regiones, pero este es un caso en el que podrían ser útiles agrupando sus métodos específicos en una región.

+0

Eso es lo que ya hago :-) Utilizo mucho las regiones y las clases parciales. – Marc

1

Si su método se vuelve demasiado grande, considere ponerlo en una clase separada o crear métodos de ayuda privada. En general, creo un nuevo método siempre que normalmente hubiera escrito un comentario.

+0

Crear un método de ayuda privada es lo que hice hasta que me enteré, pero generalmente termino con tantos métodos de ayuda privada que, un tiempo después, no sé qué método privado usa qué método privado. Es por eso que me gustaría incluir estos métodos de ayuda dentro del método que los requiere. – Marc

+0

@Marc, si su método se vuelve demasiado grande, puede ser el momento de considerar la creación de una nueva clase, pero es difícil decir cuál es el enfoque "correcto" sin conocer el código. –

2

¿Podría dar un ejemplo más concreto? Después de leer tu post Tengo la siguiente impresión, que por supuesto es sólo una suposición, debido a las informaciones limitadas:

  • Los métodos privados no están disponibles fuera de su clase, por lo que está oculto a cualquier otro código de todos modos.
  • Si desea ocultar métodos privados de otro código en la misma clase, su clase podría ser grande y podría violar la regla de responsabilidad única.
  • Echa un vistazo a los delegados anónimos y expresiones lambda. No es exactamente lo que pediste, pero podrían resolver la mayoría de tus problemas.

Achim

+0

Acepto que las expresiones lambda podrían resolver mi problema. Aunque el uso de Func I solo puede pasar 1 parámetro. Mehrdad Afshari respondió que no usaría esto para simplificar los métodos, aunque ... – Marc

0

La mejor solución es refactorizar este método para separar clase. Crea una instancia de esta clase como campo privado en tu clase inicial. Haga que el método grande sea público y refactorice el método grande en varios métodos privados, por lo que quedará muy claro lo que hace.

Cuestiones relacionadas