software sinonimo refactorizar refactorizacion refactor español ejemplos codigo java refactoring label

java - sinonimo - Refactorización de los bucles etiquetados



refactorizar js (12)

Después de convencerme de que los breaks etiquetados / continue son un "nono" total aquí , necesito ayuda para eliminar la etiqueta de mi código.

Tengo una matriz cuadrada y un vector que tiene la misma longitud. El vector ya tiene algunos valores y dependiendo de los valores de la matriz, el vector se cambia en el ciclo.

Espero, el fragmento de código es básicamente comprensible ...

vectorLoop: for( int idx = 0; idx < vectorLength; idx++) { if( conditionAtVectorPosition( v, idx ) ) continue vectorLoop; matrixLoop: for( rowIdx = 0; rowIdx < n; rowIdx++ ) { if( anotherConditionAtVector( v, rowIdx ) ) continue matrixLoop; if( conditionAtMatrixRowCol( m, rowIdx, idx ) ) continue vectorLoop; } setValueInVector( v, idx ); }

Por favor, me convence de que hay una versión más legible / mejor sin las etiquetas.


Algunos vienen con una penalización de rendimiento de ejecutar la misma prueba dos veces, lo que no siempre es trivial. La alternativa a eso es almacenar y pasar booleanos redondos, lo que se pone feo.
La pena de rendimiento es menor. Sin embargo, estoy de acuerdo en que ejecutar una prueba dos veces no es una buena solución.

Creo que la pregunta era cómo eliminar las etiquetas, no cómo optimizar el algoritmo. Me pareció que el póster original no sabía cómo usar las palabras clave ''continuar'' y ''romper'' sin etiquetas, pero, por supuesto, mis suposiciones pueden ser incorrectas.

Cuando se trata de rendimiento, la publicación no proporciona ninguna información sobre la implementación de las otras funciones, por lo que, por lo que sé, también podrían descargar los resultados a través de FTP como si se tratara de simples cálculos escritos por el compilador.

Dicho esto, hacer la misma prueba dos veces no es óptimo, en teoría.

EDITAR: Pensándolo bien, el ejemplo en realidad no es un uso horrible de las etiquetas. Estoy de acuerdo en que "goto es un no-no" , pero no por un código como este. El uso de etiquetas aquí no afecta la legibilidad del código de una manera significativa. Por supuesto, no son necesarios y pueden omitirse fácilmente, pero no usarlos simplemente porque "usar etiquetas es malo" no es un buen argumento en este caso. Después de todo, eliminar las etiquetas no hace que el código sea mucho más fácil de leer, como otros ya han comentado.


¿Esto funciona para tí? Extraje el bucle interno en un método CheckedEntireMatrix (puedes nombrarlo mejor que yo) - También mi java está un poco oxidado ... pero creo que transmite el mensaje

for( int idx = 0; idx < vectorLength; idx++) { if( conditionAtVectorPosition( v, idx ) || !CheckedEntireMatrix(v)) continue; setValueInVector( v, idx ); } private bool CheckedEntireMatrix(Vector v) { for( rowIdx = 0; rowIdx < n; rowIdx++ ) { if( anotherConditionAtVector( v, rowIdx ) ) continue; if( conditionAtMatrixRowCol( m, rowIdx, idx ) ) return false; } return true; }


@Patrick está asumiendo que llama a setValueInVector (v, idx); al final del segundo ciclo está bien. Si el código debe ser idéntico, lógicamente, se debe volver a escribir de la siguiente manera:

for( int idx = 0; idx


De leer tu código

  • Noté que eliminaste las posiciones del vector no válido en conditionAtVectorPosition y luego eliminaste las filas no válidas en anotherConditionAtVector.
  • Parece que comprobar las filas en otroConditionAtVector es redundante ya que cualquiera que sea el valor de idx, anotherConditionAtVector solo depende del índice de la fila (suponiendo que AnotherConditionAtVector no tiene efectos secundarios).

Entonces puedes hacer esto:

  • Obtenga las posiciones válidas primero usando conditionAtVectorPosition (estas son las columnas válidas).
  • A continuación, obtenga las filas válidas usando otroConditionAtVector.
  • Finalmente, use conditionAtMatrixRowCol usando las columnas y filas válidas.

Espero que esto ayude.


Fácilmente, mi buen hombre.

for( int idx = 0; idx < vectorLength; idx++) { if( conditionAtVectorPosition( v, idx ) ) continue; for( rowIdx = 0; rowIdx < n; rowIdx++ ) { if( anotherConditionAtVector( v, rowIdx ) ) continue; if( conditionAtMatrixRowCol( m, rowIdx, idx ) ) break; } if( !conditionAtMatrixRowCol( m, rowIdx, idx ) ) setValueInVector( v, idx ); }

EDITAR: Muy correcto, eres Anders. He editado mi solución para tener eso en cuenta también.


Gishu tiene la idea correcta:

for( int idx = 0; idx < vectorLength; idx++) { if (!conditionAtVectorPosition( v, idx ) && checkedRow(v, idx)) setValueInVector( v, idx ); } private boolean checkedRow(Vector v, int idx) { for( rowIdx = 0; rowIdx < n; rowIdx++ ) { if( anotherConditionAtVector( v, rowIdx ) ) continue; if( conditionAtMatrixRowCol( m, rowIdx, idx ) ) return false; } return true; }


Mirando las soluciones presentadas hasta ahora:

  • Todos parecen menos legibles que el original, ya que implican gastar más código en el mecanismo del código que en el algoritmo mismo

  • Algunos de ellos están rotos o antes de que fueran editados. Lo más condenable es el hecho de que la gente tiene que pensar bastante sobre cómo escribir el código sin etiquetas y no romper nada.

  • Algunos vienen con una penalización de rendimiento de ejecutar la misma prueba dos veces, lo que no siempre es trivial. La alternativa a eso es almacenar y pasar booleanos redondos, lo que se pone feo.

  • La refacturación de la parte relevante del código en un método es efectivamente no operativa: reorganiza la forma en que el código se presenta en el archivo, pero no tiene ningún efecto sobre cómo se ejecuta.

Todo lo cual me hace creer que, al menos en el caso de esta pregunta tal como está redactada, la etiqueta es la solución correcta y no necesita ser refactorizada. Ciertamente, hay casos en los que las etiquetas se usan de forma incorrecta y deben rediseñarse. Simplemente no creo que deba tratarse como una regla irrompible.


No estoy muy seguro de entender la primera continuación. Copiaría a Gishu y escribiría algo parecido (lo siento si hay algunos errores):

for( int idx = 0; idx < vectorLength; idx++) { if( !conditionAtVectorPosition( v, idx ) && CheckedEntireMatrix(v)) setValueInVector( v, idx ); } inline bool CheckedEntireMatrix(Vector v) { for(rowIdx = 0; rowIdx < n; rowIdx++) if ( !anotherConditionAtVector(v,rowIdx) && conditionAtMatrixRowCol(m,rowIdx,idx) ) return false; return true; }


Creo que los bucles etiquetados son tan poco comunes que puede elegir cualquier método de etiquetado que funcione para usted: lo que tiene allí hace que sus intenciones con el texto continúen perfectamente claras.

Después de liderar el proceso para sugerir refactorizar los bucles en la pregunta original y ahora ver el código en cuestión, creo que tienes un bucle muy legible allí.

Lo que había imaginado era una porción muy diferente de código: al poner el ejemplo real, puedo ver que es mucho más limpio de lo que había pensado.

Mis disculpas por el malentendido.


@ Nicolas

Algunos de ellos están rotos o antes de que fueran editados. Lo más condenable es el hecho de que la gente tiene que pensar bastante sobre cómo escribir el código sin etiquetas y no romper nada.

Tengo un punto de vista diferente: algunos de ellos están rotos porque es difícil determinar el comportamiento del algoritmo original.

Me doy cuenta de que es subjetivo, pero no tengo problemas para leer el algoritmo original. Es más corto y más claro que los reemplazos propuestos.

Lo que hacen todas las refactorizaciones en este hilo es emular el comportamiento de una etiqueta que usa otras características del lenguaje, como si estuviera transfiriendo el código a un idioma que no tenía etiquetas.


@ Sadie :

Todos parecen menos legibles que el original, ya que implican gastar más código en el mecanismo del código que en el algoritmo mismo

Externalizar el segundo bucle fuera del algoritmo no es necesariamente menos legible. Si el nombre del método está bien elegido, puede mejorar la legibilidad.

Algunos de ellos están rotos o antes de que fueran editados. Lo más condenable es el hecho de que la gente tiene que pensar bastante sobre cómo escribir el código sin etiquetas y no romper nada.

Tengo un punto de vista diferente: algunos de ellos están rotos porque es difícil determinar el comportamiento del algoritmo original.

Algunos vienen con una penalización de rendimiento de ejecutar la misma prueba dos veces, lo que no siempre es trivial. La alternativa a eso es almacenar y pasar booleanos redondos, lo que se pone feo.

La pena de rendimiento es menor. Sin embargo, estoy de acuerdo en que ejecutar una prueba dos veces no es una buena solución.

La refacturación de la parte relevante del código en un método es efectivamente no operativa: reorganiza la forma en que el código se presenta en el archivo, pero no tiene ningún efecto sobre cómo se ejecuta.

No veo el punto. Sí, no cambia el comportamiento, como ... refactorización?

Ciertamente, hay casos en los que las etiquetas se usan de forma incorrecta y deben rediseñarse. Simplemente no creo que deba tratarse como una regla irrompible.

Estoy totalmente de acuerdo. Pero como ha señalado, algunos de nosotros tenemos dificultades al refacturar este ejemplo. Incluso si el ejemplo inicial es legible, es difícil de mantener.


Esta pregunta no se trataba de optimizar el algoritmo, pero gracias de todos modos ;-)

En el momento en que lo escribí, consideré que la etiqueta continuaría como una solución legible.

Le hice una pregunta acerca de la convención (con la etiqueta en mayúsculas o no) para las etiquetas en Java.

Básicamente, cada respuesta me decía "¡no los utilices, siempre hay una mejor manera! ¡Refactor!". Entonces, publiqué esta pregunta para pedir una solución más legible (¿y por lo tanto mejor?).

Hasta ahora, no estoy completamente convencido de las alternativas presentadas hasta ahora.

Por favor no me malinterpretes Las etiquetas son malvadas la mayor parte del tiempo.

Pero en mi caso, las pruebas condicionales son bastante simples y el algoritmo se toma de un documento matemático y, por lo tanto, es muy probable que no cambie en el futuro cercano. Por lo tanto, prefiero tener todas las partes relevantes visibles a la vez en lugar de tener que desplazarme a otro método llamado checkMatrixAtRow (x).

Especialmente en algoritmos matemáticos más complejos, me resulta bastante difícil encontrar nombres de funciones "buenos", pero creo que esa es otra pregunta