una tipos procedimiento funcion example end ejemplos ejecutar developer bloques bloque begin anonimo almacenado c#

c# - tipos - procedure oracle ejemplos



¿Cuál es el valor de un bloque anónimo no asignado en C#? (10)

En C # puedes hacer un bloque dentro de un método que no está adjunto a ninguna otra declaración.

public void TestMethod() { { string x = "test"; string y = x; { int z = 42; int zz = z; } } }

Este código se compila y se ejecuta como si las llaves dentro del método principal no estuvieran allí. También note el bloque dentro de un bloque.

¿Hay un escenario donde esto sería valioso? Todavía no he encontrado ninguno, pero tengo curiosidad por conocer los hallazgos de otras personas.


Es un subproducto de una regla del analizador esa declaración es una declaración simple o un bloque. es decir, un bloque se puede usar donde quiera que una sola declaración pueda.

p.ej

if (someCondition) SimpleStatement(); if (SomeCondition) { BlockOfStatements(); }

Otros han señalado que las declaraciones variables están en el alcance hasta el final del bloque contenedor. Es bueno para vars temporales tener un alcance corto, pero nunca he tenido que usar un bloque por sí solo para limitar el alcance de una variable. Algunas veces usa un bloque debajo de una declaración de "uso" para eso.

Por lo general, no es valioso.


No tiene ningún valor aparte de la semántica y del alcance y la recolección de basura, ninguno de los cuales es significativo en este ejemplo limitado. Si crees que hace que el código sea más claro, para ti y para los demás, puedes usarlo. Sin embargo, la convención más aceptada para la clarificación semántica en el código generalmente usaría saltos de línea solo con comentarios en línea de opción:

public void TestMethod() { //do something with some strings string x = "test"; string y = x; //do something else with some ints int z = 42; int zz = z; }


En C # - como c / c ++ / java - llaves indican un alcance. Esto dicta la vida de una variable. A medida que se alcanza el paréntesis de cierre, la variable queda inmediatamente disponible para una recolección de basura. En c ++, haría que se llamara al destructor de una clase si la var representaba una instancia.

En cuanto al uso, el único uso posible es liberar un objeto grande pero tbh, establecerlo en nulo tendría el mismo efecto. Sospecho que el uso anterior probablemente sea solo para mantener a los programadores de C ++ moviéndose al código administrado en un territorio familiar y cómodo. Si realmente desea llamar a un "destructor" en c #, normalmente implementa la interfaz IDisposable y utiliza el patrón "using (var) {...}".

Oisin


Esto le permite crear un bloque de alcance en cualquier lugar. No es tan útil por sí mismo, pero puede simplificar la lógica:

switch( value ) { case const1: int i = GetValueSomeHow(); //do something return i.ToString(); case const2: int i = GetADifferentValue(); //this will throw an exception - i is already declared ...

En C # podemos usar un bloque de alcance para que los artículos declarados en cada caso estén solo en el alcance en ese caso:

switch( value ) { case const1: { int i = GetValueSomeHow(); //do something return i.ToString(); } case const2: { int i = GetADifferentValue(); //no exception now return SomeFunctionOfInt( i ); } ...

Esto también puede funcionar para gotos y etiquetas, no es que a menudo los uses en C #.


Incluso si fuera realmente útil por alguna razón (por ejemplo, control de alcance variable), lo desalentaría de tal construcción desde el punto de vista de la buena lectura del código antiguo.


Por lo que puedo ver, solo sería útil desde el punto de vista de la organización. Realmente no puedo concebir ningún valor lógico al hacer eso. Quizás alguien tenga un ejemplo apropiado.


Una razón para hacer esto es que las variables ''z'' y ''zz'' no estarían disponibles para codificar debajo del final de ese bloque interno. Cuando haces esto en Java, la JVM empuja un marco de pila para el código interno, y esos valores pueden vivir en la pila. Cuando el código sale del bloque, el marco de pila se abre y esos valores desaparecen. Dependiendo de los tipos involucrados, esto puede evitar que tenga que usar la recolección de basura y / o montón.


Un ejemplo sería si quisiera reutilizar un nombre de variable, normalmente no puede reutilizar los nombres de las variables Esto no es válido

int a = 10; Console.WriteLine(a); int a = 20; Console.WriteLine(a);

pero esto es:

{ int a = 10; Console.WriteLine(a); } { int a = 20; Console.WriteLine(a); }

Lo único que se me ocurre en este momento es, por ejemplo, si está procesando un objeto grande, y extrajo algo de información de él, y después de eso iba a realizar un montón de operaciones, podría poner el procesamiento de objetos grandes en un bloque, para que salga del alcance, luego continúe con las otras operaciones

{ //Process a large object and extract some data } //large object is out of scope here and will be garbage collected, //you can now perform other operations with the extracted data that can take a long time, //without holding the large object in memory //do processing with extracted data


La única razón práctica para que exista es si desea restringir el alcance de alguna variable cuando no existe una necesidad imperiosa de introducir ninguna otra razón para el bloqueo. En la práctica real, esto prácticamente nunca es útil.

Personalmente, supongo que desde el punto de vista del lenguaje / compilador es más fácil decir que puedes poner un bloque en cualquier lugar donde se espere una declaración, y simplemente no se salieron de su camino para evitar que lo uses sin un / para / declaración de método / etc.

Considere el comienzo de esta reciente publicación en el blog de Eric Lippert. Una instrucción if no es seguida por una sola instrucción o una cantidad de enunciados encerrados entre llaves, simplemente es seguida por una sola declaración. Cada vez que encierre entre 0 y N en llaves, usted hace que esa sección del código sea equivalente (desde el punto de vista del analizador del lenguaje) a una declaración. Esta misma práctica también se aplica a todas las estructuras de bucle, aunque, como explica el punto principal de la publicación del blog, no se aplica a los bloques try / catch / finally.

Al abordar los bloques desde ese punto de vista, la pregunta es: "¿Existe alguna razón convincente para evitar que los bloques se usen en cualquier lugar en que se pueda usar un solo enunciado?" y la respuesta es no".


Alcance y recolección de basura: cuando abandona el bloque no conectado, cualquier variable declarada en él queda fuera del alcance. Eso permite que el recolector de basura limpie esos objetos.

Ray Hayes señala que el recolector de basura .NET no recogerá inmediatamente los objetos fuera del alcance, por lo que el alcance es el principal beneficio.