Está en la página 1de 44

REFACTORING

Tabla de Contenido

1.

Introducción

 

3

1.1 Justificación

4

1.2 Objetivos

4

 

1.2.1 Objetivo General

4

1.2.2 Objetivos Específicos

4

1.3 Metas

 

5

1.4 Límites

5

1.5 Alcances

5

2. Metodología

6

2.1 Línea de Investigación

6

2.2 Métodos de Investigación

6

3. Antecedentes

7

3.1 Explicación Inicial de Conceptos

7

4. Ejemplo [2]

 

8

5. Explicación

37

5.1 Implantación de la refactorización

38

5.2 Pasos para implantar la refactorización en un equipo

38

5.3 Refactoring Continuo

39

5.4 Dificultades de la refactorización en la práctica

40

 

5.4.1

El factor humano

40

5.4.1

Trabajo en equipo

40

5.5 Refactoring a posteriori

41

5.6 Refactorización y pruebas unitarias

41

6. Ventajas

 

42

7. Desventajas

42

8. Recomendaciones

43

9. Conclusiones

 

44

10. Bibliografía

45

Documento 1

Pág. 2

Versión 1.00

1. Introducción

REFACTORING

En el presente documento tiene como objetivo introducir al programador acerca del método refactoring, mostrarle a este cómo hacer refactoring de una forma controlada y eficiente, de manera tal que no se introduzcan errores en el código si no que metódicamente se pueda mejorar la estructura del código introducido.

Para esto se planteara la teoría acerca de es refactoring y se darán ejemplos y la una discusión incluyendo código de manera que estos sean fáciles de leer y entender. Los ejemplos estarán en Java debido a que es un lenguaje muy conocido y puede ser fácilmente entendido por cualquier persona con conocimientos en programación. También es un lenguaje orientado a objetos, y los mecanismos orientados a objetos son de gran ayuda en la refactorización.

Aunque se centra en el código para lograr comprende el concepto de refactoring, este tiene un gran impacto en el diseño de sistemas. Es de vital importancia para los diseñadores y arquitectos de alto nivel para entender los principios del refactoring y usarlos en sus proyectos. Refactoring es el más presentado por un desarrollador respetado y con experiencia.

La estructuración de este documento será la siguiente

Introducción

Metodología

Antecedentes

Explicación de ¿qué es refactoring?

Ejemplos

Ventajas

Desventajas

Recomendaciones

Conclusiones

[1]
[1]

Documento 1

Pág. 3

Versión 1.00

1.1 Justificación

REFACTORING

La investigación propuesta busca, mediante la aplicación de la teoría y conceptos sobre restructuración o refactorización de código, detallar los procesos de este tipo de técnica que nos brinda la funcionalidad de cambiar el código sin perder su comportamiento externo, así como explicar las principales características de implementación durante el desarrollo de aplicaciones de software como una herramienta útil para tener un código mas entendible para los desarrolladores. Además se busca darle al lector una serie de recomendaciones para que este pueda valorar los diferentes casos en que se puede usar este tipo de herramienta, y también ofrecer una lista detallada de ventajas y desventajas que nos provee la implementación de la técnica refactorización de código en nuestras aplicaciones.

1.2 Objetivos

1.2.1 Objetivo General

Investigar, explicar y profundizar en el tema de Refactorización de código en ambientes de desarrollo de aplicaciones de software y dejar claro su concepto, además de exponer los principales componentes y características que posee y dar un ejemplo detallado de su implementación en código (este será en el lenguaje de programación Orientado a Objetos Java ya que es de los mas utilizados actualmente).

1.2.2 Objetivos Específicos

1. Explicar las principales ventajas y desventajas de utilizar la herramienta de Refactoring en el desarrollo de aplicaciones.

2. Enfatizar y explicar los detalles de implementación específicos de como hacer la refactorización de código en una arquitectura Orientada a Objetos.

3. Explicar claramente los diferentes tipos de Refactoring que se utilizan actualmente.

4. Detallar los pasos que se deben seguir cuando se implementa la estrategia de Refactoring en un equipo de trabajo.

Documento 1

Pág. 4

Versión 1.00

1.3 Metas

REFACTORING

Cubrir una gran área de conocimiento sobre la técnica de refactorización de código, analizando su implementación, así como sus conceptos y características principales.

Dar a conocer las principales ventajas y desventajas del uso de esta técnica en nuestras aplicaciones, así como brindar una lista de recomendaciones de cuando usarlo y cuando no.

Informar sobre los principales pasos a seguir para cuando se vaya a implementar esta técnica en algún equipo de trabajo, para que el código quede más ordenado y estandarizado.

1.4 Límites

A continuación se enlistan los aspectos que no serán contenidos ni analizados en la investigación:

Implementación detalla y específica sobre la técnica de refactorización de código para las tecnologías especificas, es decir, el ejemplo mostrado es una versión generalizada en el lenguaje Java de como implementar el Refactoring.

La utilización e implementación de Pruebas Unitarias y cualquier otro tipo de pruebas para la verificación de que la refactorización de código estén bien hechas y libre de errores.

1.5 Alcances

Los siguientes subtemas si están cubiertos por la Investigación:

Detalles de implementación y diversos tipos de Refactoring como los son el continuo y el A posteriori.

Definición de los pasos específicos para la implementación de Refactoring en un equipo de trabajo.

Definición y concepto sobre la factorización de código así como sus antecedentes.

Características principales y componentes de la factorización de código.

Ventajas y desventajas.

Explicación detallada de su Uso en diferentes aplicaciones.

Documento 1

Pág. 5

Versión 1.00

REFACTORING

2. Metodología

2.1 Línea de Investigación

Para la presente investigación se obtuvieron datos sobre el Tema principal Refactoring en programación. La línea de investigación siguió los siguientes subtemas principales:

Implementación de la estrategia de refactorización.

Pasos para implantar la refactorización en un equipo.

Refactoring Continuo

Dificultades de la Refactorización en la Práctica.

Refactoring a Posteriori

Refactorización y Pruebas Unitarias.

2.2 Métodos de Investigación

La técnica de recolección de información utilizada fue el análisis documental: Este alude al conjunto de conocimientos relativos a los principios, métodos y técnicas que permiten examinar, distinguir y separar cada una de las partes de un documento y analizar su forma estructural y propiedades para obtener un resultado para cierta investigación.

Se buscaron estudios previos de diversas fuentes como informes, artículos y libros publicados en la web. Así mismo, se consultaron diferentes medios visuales como animaciones, videos y presentaciones que ayudaron a enriquecer los conocimientos para la investigación.

Para llevar a cabo la investigación, primeramente se realizó una pequeña búsqueda de información para formar la propuesta de investigación. Posteriormente se procedió a recolectar más información para poder realizar un estudio detallado y completo del tema en cuestión. Finalmente se analizaron y se procesaron los datos para obtener los resultados.

Documento 1

Pág. 6

Versión 1.00

3. Antecedentes

REFACTORING

3.1 Explicación Inicial d e Conceptos

La refactorización de program as surge como herramienta necesaria para ser

procesos de mantenimiento de bido a las características esenciales del software

costos de esta fase del proceso

funcionalidad dentro del ciclo ev olutivo de las aplicaciones.

aplicada en los para reducir los

de desarrollo y como herramienta en la introdu cción de nueva

El objetivo de la refactorización mismo.

de software es principalmente mantener o aume ntar el valor del

La refactorización de código es u na de las Técnicas y/o Herramientas para tratar de hacer el código más entendible y ahorrar tiemp os, costos en el mantenimiento.

Hay dos puntos de vista, por un a parte hay muchos programadores que hacen al go en 2 líneas y

súper Eficiente pero que nadie cualquier persona.

entiende. Y hay otros que lo hacen en 10 líneas per o que entiende

¿Qué es mejor?, desde nuestro de más es un desperdicio optas modelos y técnicas propuestas funcionar muy bien.

punto de vista depende del tipo caso. Si es un pro yecto cada byte por ser óptimo, en otro caso es mejor comentar y programar con que a primera vista son muy tontas, pero a larg o plazo suelen

un sistema de mejorando su

estructura interna". Por definici ón, el proceso de refactorización de código fuente debe preservar

el comportamiento del

analogía con

la factorización de números y po linomios. Por ejemplo, puede ser fac torizado como

estructura interna que no era visible previamen te. De manera

visible puede

software de forma tal que no o altere el comportamiento externo del código,

Software refactoring surge co

mo el proceso en el cual se aplican cambios en

sistema.

El

del

software,

término

se

se aplican cambios en sistema. El del software, término se el cambio en creó la como

el

cambio

en

creó

la

como

estructura

software, término se el cambio en creó la como estructura , revelando una similar, en la

, revelando una similar, en la refactorización

frecuentemente revelar la estru ctura interna "oculta" del código original.

Documento 1

Pág. 7

Versión 1.00

REFACTORING

4. Ejemplo [2]

El ejemplo trata de un programa para calcular e imprimir una declaración de cargos de un cliente en una tienda de video. El programa se dijo que un cliente alquila películas y por cuánto tiempo. A continuación, calcula los cargos, que dependen de la duración de la película se alquila, e identifica el tipo de película. Hay tres tipos de películas: regulares (regular), niños (childrens), y estrenos (new release). Está escrito en código Java.

Además de los cargos de cálculo, la declaración también calcula los puntos frecuentes de socios, los cuales varían dependiendo de si la película es una nueva versión.

En el ejemplo en código y diagramas, se utilizara el nombre de las funciones, clases y métodos en ingles.

el nombre de las funciones, clases y métodos en ingles. Diagrama de clases con las clases

Diagrama de clases con las clases iniciales. Sólo las características más importantes se muestran.

Clase Movie

ingles. Diagrama de clases con las clases iniciales. Sólo las características más importantes se muestran. Clase

Documento 1

Pág. 8

Versión 1.00

Clase Rental

REFACTORING

Clase Rental REFACTORING Clase Costumer Método statement Diagrama de interacción del método

Clase Costumer

Clase Rental REFACTORING Clase Costumer Método statement Diagrama de interacción del método

Método statement

Clase Rental REFACTORING Clase Costumer Método statement Diagrama de interacción del método

Diagrama de interacción del método

Documento 1

Pág. 9

Versión 1.00

Código del método

REFACTORING

Código del método REFACTORING

Documento 1

Pág. 10

Versión 1.00

REFACTORING

En este caso el código no está bien diseñado, y no está orientado a objetos. Para que un programa tan simple como este, que en realidad no importa. No hay nada malo con un simple programa rápido. Pero si se trata de un fragmento representativo de un sistema más complejo, entonces tengo algunos problemas reales con este programa. Esa declaración larga en la clase de hace demasiado, muchas de las cosas que hace debe realmente ser hecho por las otras clases.

Aun así, el programa funciona. ¿No es esto sólo un juicio estético, una aversión del código feo?. Al compilador no le importa si el código es feo o limpio. Sin embargo, cuando cambiamos el sistema, hay personas involucradas, que se preocupan por esto. Un sistema mal diseñado es difícil de cambiar, y es difícil porque, es difícil de entender que los cambios son necesarios dentro de este. Si es difícil de averiguar que cambiar, hay una gran posibilidad de que el programador se cometa un error o introduzca errores dentro del código.

En este caso tenemos un cambio que los usuarios les gustaria realizar. En primer lugar quieren el statement este disponible en HTML. Se debe considerar el impacto que este cambio tendría. Como nos fijamos en el código se puede ver que es imposible volver a utilizar cualquiera de la comportamiento que tenga el método statement actual de para la versión de HTML. La única alternativa es escribir un método completamente nuevo que duplica la mayor parte del comportamiento de statement. Ahora, por supuesto, esto no es demasiado complicado el hacer esto, puede simplemente copiar el método de declaración y hacer los cambios que se necesitan.

Usted tiene que fijar tanto en statement y htmlStatement y asegurar que las revisiones son compatibles. El problema con copiar y pegar el código viene cuando se tiene que cambiar más adelante. Si usted está escribiendo un programa que no te espera cambiar, cortar y pegar está muy bien. Si el programa es de larga vida y es probable que cambie, cortar y pegar es una amenaza.

Esto me lleva a un segundo cambio. Los usuarios desean realizar cambios en la clasificación de las películas, pero todavía no han decidido sobre el cambio que se va a hacer. Tienen una serie de cambios en mente. Estos cambios afectarán la manera la que los socios pagan por las películas y la forma en que los puntos frecuentes se calculan. La única garantía de que vamos a tener, es que lo van a cambiar de nuevo en un plazo de seis meses.

El en método statement es donde se realizaran los cambios para hacer frente a cambios en la clasificación y las reglas de puntos. Sin embargo, si se copia statement a htmlStatement, tenemos que asegurarnos de que los cambios son completamente consistentes. Además, como las reglas se hacen más complejas que va a ser más difícil de averiguar dónde hacer los cambios y las más difíciles de hacerlos sin cometer un error.

Para tener este código legible y bien diseñado para los demás desarrolladores o para los futuros desarrolladores vamos a aplicar el refactoring.

Documento 1

Pág. 11

Versión 1.00

Primer paso refactoring

REFACTORING

Cada vez que hace refactoring, el primer paso es siempre el mismo. Necesito crear un conjunto sólido de pruebas para esa sección de código. Las pruebas son esenciales para evitar la mayoría de las oportunidades de introducir errores.

Debido a que el resultado que statement produce un String, puedo crear unos pocos clientes, dar a cada cliente unos pocos alquileres de diversos tipos de películas, y generar los statement String. Luego se debe realizar una comparación entre la nuevo String y algunas String de referencia que he comprobado de antemano.

Una parte importante de las pruebas es la forma en que informan sobre sus resultados. O bien decir "OK" o visto bueno, lo que significa que todas los String son idénticos a los de referencia, o imprimir una lista de fracasos con los que resultaron de otra manera. Las pruebas por lo tanto son de auto-comprobación. Es de vital importancia para realizar pruebas de comprobación en sí mismo, si no lo hace, se termina gastando tiempo revisando algunos números de la prueba en contra de algunos números del sistema anterior.

Descomposición y la redistribución de la Declaración del Método

La meta primera y más obvia de mi atención es el método statement es demasiado largo. Cuando se mira un método a largo como ese, se debe buscar descomponer el método en pedazos más pequeños que tienden a hacer que las cosas sean más manejables y más fáciles de trabajar y moverse.

El primer paso es encontrar un grupo lógico de código y utilizar el método de extracción. Realizando un cambio dentro de la declaración del código extrayendo una gran parte de este.

Al extraer un método, como en cualquier refactoring, se necesita saber que puede salir mal. Si realiza la extracción mal, se podría introducir un error en el programa. Así que antes de hacer el refactoring tengo que encontrar la manera de hacerlo con seguridad.

En primer lugar se debe mirar en el fragmento de código correspondiente a las variables que son locales en el ámbito de aplicación para el método que estamos viendo (variables locales y parámetros). Este segmento de código utiliza dos: each y thisAmount. De estos each no se modifica el código, pero thisAmount si se modifica. Cualquier variable no modificada que pueda pasada como un parámetro. Con las variables modificadas necesitan más cuidado. Si sólo hay uno, puedo volver. temp se inicializa a 0 en el ciclo y no se altera hasta que el switch cambia. Así que sólo se puede asignar el resultado.

Documento 1

Pág. 12

Versión 1.00

REFACTORING

Las dos páginas siguientes muestran el código antes y después de refactoring. El código que se esta extrayendo desde el original, y cualquier cambio en el nuevo código estará en negrita.

El código que se esta extrayendo desde el original, y cualquier cambio en el nuevo código

Documento 1

Pág. 13

Versión 1.00

REFACTORING

REFACTORING Cada vez que realiza un cambio como éste, se debe compilar y probar. En este

Cada vez que realiza un cambio como éste, se debe compilar y probar. En este código existe un error en amountFor bebido a que el tipo de retorno es un int lugar de double

Documento 1

Pág. 14

Versión 1.00

REFACTORING

REFACTORING Ahora que he dividido el método original en pedazos, se puedo trabajar en ellos por

Ahora que he dividido el método original en pedazos, se puedo trabajar en ellos por separado. Al no tener las variables con nombre

Aquí está el código original:

por separado. Al no tener las variables con nombre Aquí está el código original: Aquí está

Aquí está el código modificado:

por separado. Al no tener las variables con nombre Aquí está el código original: Aquí está

Documento 1

Pág. 15

Versión 1.00

REFACTORING

Una vez que he hecho el renombramiento de la variable, se compila y prueba para asegurarse de que exista error alguno.

Moviendo Amount Calculation

Cuando se observa amountFor, se puede ver que utiliza la información de la renta, pero no utiliza la información del cliente.

de la renta, pero no utiliza la información del cliente. El método es en el objeto

El método es en el objeto está equivocado y no pertenece a la clase customer, en la mayoría de los casos, un método que se encuentra dentro del objeto utiliza los datos de este, por lo que el método debe ser trasladado a la renta. Para hacer esto mover el método. Con esto, primero copia el código a alquiler, ajustándolo la a su nueva clase y compilar para que quede de la siguiente manera:

primero copia el código a alquiler, ajustándolo la a su nueva clase y compilar para que

Documento 1

Pág. 16

Versión 1.00

REFACTORING

En este caso, cuando se introduce el método en la clase customer significa la eliminación del parámetro, también cambió el nombre del método.

Ahora puede probar para ver si este método funciona. Para ello puedo reemplazar el código de Customer.amountFor delegar este nuevo método.

el código de Customer.amountFor delegar este nuevo método. Se compila para comprobar que no existan errores

Se compila para comprobar que no existan errores en el código. El siguiente paso es encontrar todas las referencias al método antiguo y ajustarlas la referencias para utilizar el nuevo método:

y ajustarlas la referencias para utilizar el nuevo método: En este caso, este paso es fácil,

En este caso, este paso es fácil, ya que acaba de crear el método, que se encuentra en un solo lugar. En general, sin embargo, hay que "encontrar" ese cambio a través de todas las clases que puedan estar utilizando este método:

Documento 1

Pág. 17

Versión 1.00

REFACTORING

REFACTORING Cuando he hecho el cambio a las clases, lo siguiente es quitar el viejo método.

Cuando he hecho el cambio a las clases, lo siguiente es quitar el viejo método. El compilador debe decirme si me perdí nada. Entonces prueba para ver si puede existir error en el código.

prueba para ver si puede existir error en el código. Estado de las clases después de

Estado de las clases después de mover el método charge

Se puede dejar el método viejo que delegar hacia el nuevo método. Esto es útil si se trata de un método público y no quiere cambiar la interfaz de la otra clase.

Documento 1

Pág. 18

Versión 1.00

REFACTORING

Volviendo a Customer.statement.

REFACTORING Volviendo a Customer.statement. Se debe notar que thisAmount es ahora redundante. Se establece en el

Se debe notar que thisAmount es ahora redundante. Se establece en el resultado de each.charge y no cambia después. Así que puede eliminar mediante el uso de thisAmount Reemplazando Temp con el Query

Documento 1

Pág. 19

Versión 1.00

REFACTORING

REFACTORING Una vez hecho el cambio se debe compilar y probar para asegurarse de que no

Una vez hecho el cambio se debe compilar y probar para asegurarse de que no exista algún error en el código.

Lo ideal sería deshacerse de las variables temporales tanto como sea posible. Los temporales son a menudo un problema, puesto que causa que muchos de los parámetros pasen cuando no tiene que hacerlo, y puede perder la pista de lo que ellos transmiten. Por supuesto, hay un precio a pagar, ahora charge se calcula en dos ocasiones. Pero es fácil de optimizar que en la clase Rental y hacerla mucho más eficaz si el código está correctamente factorizado.

Documento 1

Pág. 20

Versión 1.00

REFACTORING

La extracción de los puntos más frecuentes

El siguiente paso es hacer una cosa similar para los puntos frecuentes de los socios. Las reglas varían con la película, aunque hay una menor variación que con charge. Parece razonable poner esta responsabilidad en la clase Rental. En primer lugar tenemos que usar extraer el método de los puntos frecuentes del socio (en negrita):

el método de los puntos frecuentes del socio (en negrita): Se deben observar el uso de

Se deben observar el uso de variables locales. Una vez más each se utiliza y se puede pasar como un parámetro. El otro temporal usado es frequentRenterPoints. En este caso frequentRenterPoints tiene un valor previo. El código del método que se extrajo no lee el valor, sin embargo, no es necesario pasarlo como parámetro si se lo añadimos ala asignacion.

Se realizo la extracción, compilo y probo, para luego hacer un movimiento, compilado y probado de nuevo. Con esto refactoring en pequeños los pasos es la mejor practica para evitar posibles complicaciones.

Documento 1

Pág. 21

Versión 1.00

REFACTORING

REFACTORING Resumiendo los cambios que acaba de hacer con un antes y después se debe de
REFACTORING Resumiendo los cambios que acaba de hacer con un antes y después se debe de

Resumiendo los cambios que acaba de hacer con un antes y después se debe de actualizar el diagrama de las clases quedando de la siguiente manera:

el diagrama de las clases quedando de la siguiente manera: Diagrama de clase antes de la

Diagrama de clase antes de la extracción y el movimiento del cálculo puntos frecuentes.

extracción y el movimiento del cálculo puntos frecuentes. Diagrama de secuencia antes de la extracción y

Diagrama de secuencia antes de la extracción y el movimiento del cálculo puntos frecuentes

Documento 1

Pág. 22

Versión 1.00

REFACTORING

REFACTORING Diagrama de clases después de la extracción y el movimiento del cálculo de puntos frecuentes

Diagrama de clases después de la extracción y el movimiento del cálculo de puntos frecuentes

y el movimiento del cálculo de puntos frecuentes Diagrama de Secuencia después de la extracción y

Diagrama de Secuencia después de la extracción y el movimiento del cálculo puntos frecuentes

Documento 1

Pág. 23

Versión 1.00

REFACTORING

Removiendo las variables temporales

Como se observo antes, las variables temporales puede ser un problema. Sólo son útiles dentro de su propia rutina, por lo tanto no utilizarlas en rutinas largas y complejas. En este caso tenemos dos variables temporales, los cuales están siendo utilizados para obtener un total del alquiler del cliente, tanto las versiones ASCII y HTML requieren estos totales. Lo ideal sería reemplazar estas variables con Query’s para reemplazar TotalAmount, frequentRentalPoints ya que estos son accesibles a cualquier método en la clase y fomentar así un diseño más limpio, sin métodos largos y complejos:

un diseño más limpio, sin métodos largos y complejos: Comenzamos sustituyendo TotalAmount con un método charge

Comenzamos sustituyendo TotalAmount con un método charge en el customer

limpio, sin métodos largos y complejos: Comenzamos sustituyendo TotalAmount con un método charge en el customer

Documento 1

Pág. 24

Versión 1.00

REFACTORING

REFACTORING Este no es un caso de reemplazar simplemente la variable temporal con el query ,

Este no es un caso de reemplazar simplemente la variable temporal con el query, TotalAmount fue asignado a dentro de ciclo, así que tengo que copiar el ciclo en el método query.

así que tengo que copiar el ciclo en el método query . A continuación se muestra

A

continuación se muestra el cambio del refactoring en los diagramas de clases e interacción para

el

método statement

Documento 1

Pág. 25

Versión 1.00

REFACTORING

REFACTORING Diagrama de clase antes de la extracción de los totales Diagrama de secuencia antes de

Diagrama de clase antes de la extracción de los totales

Diagrama de clase antes de la extracción de los totales Diagrama de secuencia antes de la

Diagrama de secuencia antes de la extracción de los totales

Diagrama de secuencia antes de la extracción de los totales Diagrama de clase después de la

Diagrama de clase después de la extracción de los totales

Diagrama de clase después de la extracción de los totales Diagrama de secuencia después de la

Diagrama de secuencia después de la extracción de los totales

En la mayoría de los casos el refactoring ayuda reducir la cantidad de código, pero éste se incrementa. Esto se debe a Java que requiere una gran cantidad de estados para establecer un ciclo incrementa. Incluso un simple ciclo con una línea de código por cada elemento, tiene seis líneas de apoyo a su alrededor. Es un lenguaje que es obvio para cualquier programador, pero es un montón de líneas de todos modos.

Documento 1

Pág. 26

Versión 1.00

REFACTORING

La otra preocupación con este refactoring se encuentra en el rendimiento. El antiguo código ejecutado el "while" una vez, el nuevo código se ejecuta en tres ocasiones. Un ciclo que toma mucho tiempo puede perjudicar el rendimiento. Muchos programadores no harían esto sólo por esta razón. Pero tenga en cuenta las palabras si y poder. No se puede decir cuánto tiempo necesita el ciclo para calcular o si el ciclo se llama a muchas veces como para que se afecte el rendimiento general del sistema. Al optimizar tendrá que preocuparse por ello, pero entonces estará en una posición mucho mejor para hacer algo al respecto, y usted tendrá más opciones para optimizar la eficiencia.

Ahora los query están disponibles para cualquier código escrito en la clase customer. Ellos pueden ser fácilmente añadidos a la interfaz de la clase siendo accedidos por otras partes del sistema que necesite esta información. Se puede ver la diferencia de inmediato con el htmlStatement.

puede ver la diferencia de inmediato con el htmlStatement . Extracción los cálculos que se puede

Extracción los cálculos que se puede crear del método htmlStatement y reutilizar todo el código de cálculo que estaba en el método de declaración original. No copiar y pegar, así que si cambian las reglas de cálculo de estos, sólo tienen un lugar en el código al cual ir. Cualquier otro tipo de declaración va a ser muy rápida y fácil de preparar.

Parte del código se copia de la versión ASCII, debido principalmente a la creación de la ciclo. Realizar un refactoring adicional ayuda limpiar eso.

Pero ahora los clientes están pidiendo a gritos otra vez, ellos se están preparando para cambiar la clasificación de las películas en la tienda. Todavía no está claro qué cambios quieren hacer, pero parece que las clasificaciones se van a introducir, y los ya existentes podrían cambiar, los cargos puntos frecuentes de los clientes según las clasificaciones son los que deciden. Por el momento, este tipo de cambio es difícil. Se debe de entrar en el charge y los métodos de puntos frecuentes y alterar el código para hacer cambios a las clasificaciones de películas.

Documento 1

Pág. 27

Versión 1.00

REFACTORING

Sustitución de la lógica condicional en el código del Precio con polimorfismo

La primera parte de este problema es cambio en la declaración del código. Es una mala idea para hacer un switch basado en atributos de otro objeto. Si tiene que usar el switch en la declaración, esta se debe realizar con datos propios.

en la declaración, esta se debe realizar con datos propios. Esto implica que getCharge debe pasar

Esto implica que getCharge debe pasar a Movie

propios. Esto implica que getCharge debe pasar a Movie Para que esto funcione se tuvo que

Para que esto funcione se tuvo que pasar la duración del alquiler, que es uno de los datos de la clase rental. El método utiliza dos piezas de datos, la duración del alquiler y del tipo de la película. ¿Por qué prefieren pasar la duración del alquiler de la película en lugar del tipo de película para el alquiler? Esto se debe a los cambios propuestos son todos acerca de la adición de nuevos tipos. La información de tipo general, tiende a ser más volátil. Si puedo cambiar el tipo de película, quiero

Documento 1

Pág. 28

Versión 1.00

REFACTORING

que el menor efecto posible, por lo que prefiero, para calcular el charge, este se encuentre dentro de la película.

Se compilado el método en Movie y luego se cambió el getCharge en la clase Rental para utilizar el nuevo método.

en la clase Rental para utilizar el nuevo método. Diagrama de clases antes de pasar el

Diagrama de clases antes de pasar el método Movie

método. Diagrama de clases antes de pasar el método Movie Diagrama de clases después de pasar

Diagrama de clases después de pasar el método Movie

Movie Diagrama de clases después de pasar el método Movie Una vez que me movido el

Una vez que me movido el método getCharge, se hace lo mismo con el cálculo puntos frecuentes. Esto mantiene a las dos cosas que varían en la misma clase:

, se hace lo mismo con el cálculo puntos frecuentes. Esto mantiene a las dos cosas

Documento 1

Pág. 29

Versión 1.00

Por último herencia

REFACTORING

Tenemos varios tipos de película que tienen diferentes formas de responder la misma pregunta. Esto suena como un trabajo para las subclases. Podemos tener tres subclases de película, cada uno de ellos puede tener su propia versión de la carga.

uno de ellos puede tener su propia versión de la carga. Usando herencia en Movies Esto

Usando herencia en Movies

Esto me permite reemplazar el cambio en la declaración mediante el uso de polimorfismo. Lamentablemente tiene un defecto, que es menor y no funciona. Una película puede cambiar su clasificación durante su vida útil. Un objeto no puede cambiar su clase durante su vida útil. Hay una solución, la cual es aplicar el patrón State pattern.

solución, la cual es aplicar el patrón State pattern . Usando el patrón en Movie Mediante

Usando el patrón en Movie

Mediante esta adición podemos hacer de la creación de subclases del código objeto, precio y cambiar el precio cada vez que necesitamos. Si usted está familiarizado con la Gang of four patterns (nombre con el que se conoce comúnmente a los autores del libro Design Patterns), se puede preguntar, "¿Es esto un estado, o es una estrategia?" ¿El rango de precios representan un algoritmo para calcular el precio (en cuyo se puede llamarlo Pricer o PricingStrategy de manera que sean nombres significativos), o representa un estado de la película (Star Trek X es una nueva versión). En esta etapa, la elección del modelo y nombre refleja la forma en que la que quiere pensar acerca de la estructura. En este momento se está pensando en esto como un estado de

Documento 1

Pág. 30

Versión 1.00

REFACTORING

película. Si más tarde decide una estrategia para comunicar mejor la intención mejor por lo que aplicar refactoring para tener estos cambios en cuenta.

Para introducir el state pattern se utilizaran tres refactorings. En primer lugar se va a mover el comportamiento del código al state pattern reemplazando el código con el Estado/Estrategia.

pattern reemplazando el código con el Estado/Estrategia. Se ajusta el método Luego de compilar y probar

Se ajusta el método

el código con el Estado/Estrategia. Se ajusta el método Luego de compilar y probar para asegurarse

Luego de compilar y probar para asegurarse de que no existan errores, se puede añadir las nuevas clases. Que proporcionan el código de comportamiento en el objeto de precio. Se puede hacer esto con un método abstracto sobre los métodos de precios y concretos en las subclases:

objeto de precio. Se puede hacer esto con un método abstracto sobre los métodos de precios

Documento 1

Pág. 31

Versión 1.00

REFACTORING

Se compilan las clases nuevas en este punto. Ahora se cambiar el código de acceso en Movie para precio en la nueva clase:

el código de acceso en Movie para precio en la nueva clase: Esto significa reemplazar el

Esto significa reemplazar el campo código de precio, con un campo de precio, y el cambio de los métodos de acceso:

un campo de precio, y el cambio de los métodos de acceso: Ahora se compilar y

Ahora se compilar y prueban. Los métodos más complejos, no se dan cuenta que el mundo ha cambiado. Ahora aplico el muevo el método getCharge:

Los métodos más complejos, no se dan cuenta que el mundo ha cambiado. Ahora aplico el

Documento 1

Pág. 32

Versión 1.00

Es un simple movimiento

REFACTORING

Es un simple movimiento REFACTORING Una vez que se movió se puede empezar a usar reemplazar

Una vez que se movió se puede empezar a usar reemplazar las condiciones con polimorfismo

un simple movimiento REFACTORING Una vez que se movió se puede empezar a usar reemplazar las

Documento 1

Pág. 33

Versión 1.00

REFACTORING

Se toma una parte de la declaración del caso a la vez y crear un método de reemplazo, empezando con RegularPrice:

crear un método de reemplazo, empezando con RegularPrice : Esto anula la declaración en el caso

Esto anula la declaración en el caso del padre, que acaba de dejar como está y se pasa a compilar y probar este caso luego tomar la siguiente etapa de compilación, y la prueba.

luego tomar la siguiente etapa de compilación, y la prueba. Cuando se ha realizado esto con

Cuando se ha realizado esto con todos los casos, declaro el método abtracto de Price.getCharge:

los casos, declaro el método abtracto de Price.getCharge: Ahora hace lo mismo procedimiento getFrequentRenterPoints:

Ahora hace lo mismo procedimiento getFrequentRenterPoints:

los casos, declaro el método abtracto de Price.getCharge: Ahora hace lo mismo procedimiento getFrequentRenterPoints:

Documento 1

Pág. 34

Versión 1.00

REFACTORING

En primer lugar se mueve en el método de precio:

REFACTORING En primer lugar se mueve en el método de precio: En este caso, sin embargo,

En este caso, sin embargo, cree un método abstracto para la superclase. En lugar de eso, cree un método reemplazar los nuevos lanzamientos y dejar a un método definido (por defecto) de la superclase:

dejar a un método definido (por defecto) de la superclase: Poner en el state pattern fue

Poner en el state pattern fue un gran esfuerzo pero la ganancia es, que si cambia cualquier comportamiento de precios, o añaden nuevos precios, el cambio será mucho más fácil de hacer. El resto de la aplicación no conoce el uso del state pattern. En un sistema más complejo, con precios que dependen de una docena de métodos, esto haría una gran diferencia. Todos estos cambios fueron pequeños pasos.

Una vez terminado el segundo gran refactoring del código. Va a ser mucho más fácil cambiar la estructura de clasificación de películas, y para alterar las reglas de cobro y el sistema de puntos frecuente. A continuación se muestra el modelo del Estado que trabaja con la información de los precios.

se muestra el modelo del Estado que trabaja con la información de los precios. Interacciones usando

Interacciones usando state pattern

Documento 1

Pág. 35

Versión 1.00

REFACTORING

REFACTORING diagrama de clase después de la adición del state pattern Este es un ejemplo simple,

diagrama de clase después de la adición del state pattern

Este es un ejemplo simple, pero da la noción de que es el refactoring se aplico este varias ocasiones con los métodos de Extraer, Mover, y reemplazo con polimorfismo. Todo ello conduce tener, mejor distribuidas las responsabilidades de manera que el código que es más fácil de mantener. La lección más importante de este ejemplo es el ritmo del refactoring: prueba, un pequeño cambio, de prueba, un pequeño cambio, de prueba, un pequeño cambio y es que este ritmo es el que permite refactoring pueda realizarse rápidamente y con seguridad.

Documento 1

Pág. 36

Versión 1.00

5. Explicación

REFACTORING

La refactoring es uno de los nuevos conceptos que se han introducido en la terminología del mundo del desarrollo. La idea de refactorización no es nueva, lo que resulta novedoso es la forma en que se lleva a cabo, una forma ágil y agresiva, pero al tiempo ordenada y segura. ¿Qué significa refactoring? refactoring es realizar modificaciones en el código con el objetivo de mejorar su estructura interna, sin alterar su comportamiento externo, no es una técnica para encontrar y corregir errores en una aplicación, puesto que su objetivo no es alterar su comportamiento externo. De hecho, no modificar el comportamiento externo de la aplicación es uno de los pilares de cualquiera de las prácticas que forman parte de la técnica, para lo que en muchas ocasiones se hace uso de las pruebas unitarias.

La esencia de esta técnica consiste en aplicar una serie de pequeños cambios en el código manteniendo su comportamiento. Cada uno de estos cambios debe ser tan pequeño que pueda ser completamente controlado por nosotros sin miedo a equivocarnos. Es el efecto acumulativo de todas estas modificaciones lo que hace de la refactoring una potente técnica.

El objetivo final del refactoring es hacer el software más fácil de comprender y modificar. pero ¿por qué aplicar refactoring? para responder esto se toman en cuenta cuatro aspectos importantes: la

Calidad: refactoring es un continuo proceso de revisión sobre código que permitiendo que generar código sencillo y bien estructurado, de manera que cualquiera con conocimientos en programación pueda leer y entender sin necesidad de estado en el equipo de desarrollo.

Eficiencia: mantener un buen diseño y un código estructurado es la forma más eficiente de desarrollar ayudando esto a evitar la duplicación de código y simplificar, de manera que ayuda a la escalabilidad del software solución.

Diseño evolutivo: cuando se está comenzando a desarrollar cada artefacto que se esté obteniendo de cada etapa, son documentos vivos ya que al principio del proyecto no

están suficientemente especificados y debemos abordar el diseño de una forma gradual donde se van añadiendo nuevas funcionalidades según va avanzando. refactoring nos permitirá ir evolucionando el diseño según incluyamos nuevas funcionalidades, lo que implica muchas veces cambios importantes en la arquitectura, añadir cosas y borrar otras.

Evita reescribir el código: En la mayoría de los casos refactoring es mejor que rescribir o duplicar el código. Es difícil tratar de comprender un código que no conocemos y que no sigue los estándares que uno utiliza, pero eso no es motivo para empezar de cero.

Documento 1

Pág. 37

Versión 1.00

REFACTORING

5.1 Implantación de la refactorización

En el caso de comenzar un proyecto desde cero, refactoring debe ser un proceso continuo en la práctica ya que trae un gran número de beneficios y evita de forma natural algunos peligros mencionados. Sin embargo, no siempre se parte de cero, y lo habitual es encontrarnos con código cuyo diseño o estructura está lejos de ser los óptimos. Esta situación puede darse cuando tenemos que ampliar la funcionalidad de código previamente existente o simplemente porque en un proyecto empezado desde cero no se detectó la necesidad del uso refactoring a tiempo. En estos casos nos encontramos con un refactoring que se debe hacer a posteriori y deben tomarse medidas específicas para que afecte lo menos posible al ritmo normal de desarrollo.

5.2 Pasos para implantar la refactorización en un equipo

Implantar la refactorización debe realizarse de una manera progresiva. En la implantación de esta técnica es necesario seguir los siguientes pasos:

Escribir pruebas unitarias y funcionales: refactoring sin pruebas unitarias y funcionales resulta demasiado costoso y de mucho riesgo.

Usar herramientas especializadas (opcional): refactoring en muchas ocasiones obligan a pequeñas modificaciones muy simples en muchas clases de nuestro código. Con herramientas especializadas estas refactorizaciones se realizan automáticamente y sin riesgo.

Dar formación sobre patrones de refactoring y de diseño. Una buena base teórica sobre los refactoring más comunes permite al programador detectar problemas en el código de los que no es consciente y que harán que su código se degrade progresivamente.

Refactoring de los principales fallos de diseño: Nuestra recomendación es comenzar realizando refactoring concretos que permitan corregir los principales fallos de diseño, como puede ser código duplicado.

Comenzar con el refactoring en el código tras añadir cada nueva funcionalidad en grupo. Una vez corregido los errores del código existente, la mejor manera de aplicar refactoring es el añadir una nueva funcionalidad, de manera que se desarrolle de la manera más eficiente. Realizar discusiones en grupos sobre la conveniencia aplicar refactoring suele ser muy productivo.

Implantar refactoring continuo. Esta es la última fase y es cuando cada desarrollador incorpora el uso de refactoring como una tarea dentro de su proceso de desarrollo de Software.

Documento 1

Pág. 38

Versión 1.00

REFACTORING

5.3 Refactoring Continuo

Es una práctica que consiste en mantener el diseño siempre correcto, utilizando refactoring siempre que sea posible, después de añadir una nueva funcionalidad.

Dado que el refactoring supone un cambio en la estructura del código sin cambiar la funcionalidad, cuanto mayor sea el cambio en la estructura más difícil será garantizar que no ha cambiado la funcionalidad. Dicho de otra forma, cuanto mayor sea el refactoring aplicado en el código, mayor será el número de elementos implicados y mayor será el riesgo de que el sistema deje de funcionar. El tiempo necesario para llevarla a cabo también aumenta y por tanto el costo de realizar esta tarea se multiplica.

Cuando un diseño no es óptimo y necesita aplicar refactoring, cada nueva funcionalidad contribuye a empeorar el diseño un poco más. Por ello cuanto más tiempo esperamos mayor refactoring necesita en el proyecto.

Esta es la mayor de las justificaciones de una refactoring continuo, que trata de evitar refactoring en grandes bloques, si no haciendo refactoring en pequeñas escala muy a menudo.

En

funcionalidad.

concreto

el

aplicar

refactoring

de

forma

inmediata,

cuando

se

incluye

de

una

Las claves para poder aplicar refactoring continuo son:

nueva

Concienciación del desarrollador y todo el equipo de desarrollo dentro del proyecto.

Habilidad o conocimientos necesarios para identificar si es necesario aplicar refactoring.

Compartir con todo el equipo de desarrollo la visión de una arquitectura global que guíe a todos en el uso de refactoring, de manera que todos vallan en una misma dirección.

Lo más habitual es que al implementar una funcionalidad y dejar los tests pasando satisfactoriamente, estos mismos tests nos garantizarán que el código sigue funcionando después del refactoring.

Sin embargo no siempre resulta evidente para todos los desarrolladores la necesidad de utilizar refactoring en algún caso, por lo que el uso de herramientas pueden emplearse como ayuda para identificar donde se debería de aplicar. En cualquier caso es importante que estas herramientas no sustituyan nunca al sentido común y se usen únicamente como ayuda.

El principal riesgo del refactoring continuo consiste en adoptar posturas excesivamente exigentes

o criterios excesivamente personales respecto a la calidad del código. Cuando esto ocurre se acaba dedicando más tiempo al cómo y dónde se debe aplicar refactoring que a desarrollar el software. La propia presión para añadir nuevas funcionalidades a la mayor velocidad posible que impone el mercado es suficiente en ocasiones para prevenir esta situación.

Si se mantiene bajo unos criterios razonables y se realiza de forma continuada el refactoring, debe

tender a ocupar una parte pequeña en relación al tiempo dedicado a las nuevas funcionalidades.

Documento 1

Pág. 39

Versión 1.00

REFACTORING

La consecuencia inmediata de la aplicación de esta práctica suele ser la evolución de la arquitectura inicial, en beneficio de un código bien estructurado, de una arquitectura orientada en todo momento a la funcionalidad implementada y por tanto, clara y sencilla, características necesarias para que un código sea mantenible.

5.4 Dificultades de la refactorización en la práctica

En un proyecto real hay que ser consciente de que no utilizar refactoring a tiempo un diseño puede tener consecuencias muy negativas, pero a la vez debe tener en cuenta que el tiempo dedicado al uso refactoring no suele ser considerado como un avance del proyecto, por los usuarios, clientes o gestores del mismo. Otros factores clave para una correcta aplicación del refactoring, son la forma en que afecta a otros miembros del equipo, el hecho de que un desarrollador realice refactoring sobre el código en el que todos están trabajando, el que un refactoring provoque que el código esté mucho tiempo sin funcionar o el efecto negativo de no utilizarlo, en el ánimo de los desarrolladores por la sensación de no estar haciendo un trabajo de calidad.

5.4.1 El factor humano

Una realidad a veces olvidada es que cualquier desarrollador prefiere hacer código de calidad, que

esta realidad a veces queda oculta debido a condiciones de presión excesiva o menosprecio del trabajo técnico. En este sentido refactoring es una forma de mejorar la calidad y por tanto es una forma de hacer que el desarrollador esté más orgulloso de su trabajo, pero también hay un peligro en este hecho y tratar de conseguir un resultado de calidad puede llegar a generar un número excesivo del uso del refactoring dando vueltas sobre diseños similares una y otra vez.

Una posible solución consiste en mantener el refactoring bajo control, definir claramente los objetivos antes de comenzar y estimar su duración.

5.4.1 Trabajo en equipo

Un equipo de desarrollo debe ser uno. Todos los miembros del equipo deben conocer la arquitectura en cada momento, el estado actual, los problemas que tenemos y el objetivo que se busca. Una reunión diaria es una práctica que facilita la comunicación entre todos los miembros del equipo, y supone una práctica que proporciona un momento a todos los miembros del grupo

para plantear sus ideas, dudas e inquietudes respecto al proyecto.

Cuando un desarrollador hace refactoring, afecta al resto del equipo. En este sentido, uso interno de este es menos problemático, pero con las arquitecturales es necesario aplicar refactoring, se debe tener mucho cuidado ya que supone cambios en un gran tamaño en el código y por tanto es probable que se afecte el código fuente de los archivos que están siendo trabajados por los otros desarrolladores. La comunicación y coordinación entre los afectados es fundamental para que esto no se convierta en un problema. Por tanto es necesario que en la reunión diaria del equipo, donde se planteen las problemas de este tipo, de esta forma se sabrá en todo momento quienes son los afectados y cuál es el objetivo de la uso refactoring en algún área del código. De esta forma se promueve la colaboración de todos en el refactoring arquitectural que se va a llevar a cabo.

Documento 1

Pág. 40

Versión 1.00

REFACTORING

5.5 Refactoring a posteriori

Los cambios estructurales que se realizan un tiempo después de la implementación de la funcionalidad existente. Existen varios motivos para encontrarse con esta situación. Algunos de ellos son:

Un equipo comienza a trabajar con código desarrollado por un equipo anterior que o bien no tiene buena calidad o bien no está preparado para que se incorporen nuevas funcionalidades.

Se ha aplicado refactoring continuo pero la calidad del código o el diseño se ha degradado porque no se identificó a tiempo la necesidad o bien se equivocó cuando se aplico esta.

Este tipo de refactoring tiene un gran riesgo ya que los que nos encontramos con refactoring continuo. Otra característica del refactoring es que afectan no sólo al desarrollador o desarrolladores que van a aplicar, sino a todos aquellos que trabajan con la parte del código que se ve afectada por este proceso ya que por un lado no pueden trabajar con el código o deben hacerlo con mayor precaución durante un tiempo; y por otro cuando vuelvan a trabajar con él se encontrarán con un diseño desconocido. La mejor estrategia a seguir en estos casos es tratar de dividir el refactoring en el mayor número de pasos pequeños. Tras cada paso el código debe seguir funcionando sin fallos.

Antes de abordar cada uno de estos pasos se debe comunicar a todas las personas afectadas por los cambios que se van a realizar. De esta forma se evita que cuando vuelvan a trabajar con ese código se encuentren con un panorama completamente desconocido. En ocasiones también es recomendable dar explicaciones después para explicar el diseño final. Si este tipo de explicaciones deberían de ser frecuentemente, la solución no es no realizarlas, sino identificar los motivos de tanta refactoring a posteriori, probablemente sea necesario aplicar refactoring continuo en un mayor grado.

5.6 Refactorización y pruebas unitarias

La existencia de pruebas automatizadas facilita enormemente el refactoring. Los principales motivos son:

El riesgo disminuye, dado que es posible comprobar cuando esta concluye que todo sigue funcionando satisfactoriamente.

El desarrollador que realiza el refactoring puede comprobar que no ha estropeado la funcionalidad implementada por otros. Evita efectos colaterales.

El tiempo necesario para comprobar que todo sigue funcionando es menor, lo que permite avanzar en pasos más pequeños si se desea.

Refactoring sin tests es una actividad de alto riesgo y no debe hacerse salvo para los refactoring más simples y realizadas con herramientas especializadas. En ocasiones incluso algunas refactoring muy pequeños pueden provocar la aparición de bugs muy difíciles de identificar a posteriori.

Documento 1

Pág. 41

Versión 1.00

REFACTORING

En este sentido es muy importante resaltar la importancia de que las pruebas tanto funcionales como unitarias que comprueben que el código bajo prueba, funcione correctamente independientemente de cómo esté implementado. Cuanto mayor sea el acoplamiento de la prueba con la implementación, mayores serán los cambios que habrá que realizar en esta cuando se lleve a cabo, en refactoring grandes, que afectan al diseño del código significativamente, obligarán a realizar cambios en las pruebas. En este sentido también resulta útil pensar que antes usar el refactoring, se deben ver cómo van a afectar a los tests y cómo podemos usarlos en nuestro beneficio. La mejor solución es prevenir este refactoring grande es aplicando refactoring continuo y en proporciones más pequeñas. Pero una vez nos encontramos con esta situación, es recomendable cambiar las pruebas antes o a la vez que el código, de esta forma las pruebas colaborarán guiando el proceso.

6. Ventajas

Refactoring continuo tiene dos ventajas principalmente:

• El código afectado es el mismo que el que se modificó para añadir la funcionalidad y por tanto se reduce o evita completamente los inconvenientes para otros desarrolladores.

• El tiempo que se debe dedicar es reducido dado que en ese momento se tiene un conocimiento preciso del código que se verá afectado.

7. Desventajas

Además de la evidente pérdida de tiempo, refactoring puede llevar a dos efectos negativos. El primero, es que la modificación del código incremente la complejidad de nuestro diseño, que es justo el efecto contrario del que intentábamos lograr al aplicarlo. Por otro, es habitual fomentar la sensación al desarrollador o bien de todo el equipo de que no se está avanzando. Una sensación que conduce a repercusiones anímicas negativas.

A veces, el no comentar con el resto del equipo un refactoring que parece muy necesario, puede afectar a otros compañeros y de los que no éramos conscientes.

En refactoring grandes, que afectan al diseño del código significativamente, obligarán a realizar cambios en las pruebas. Esto provoca una situación incómoda, las pruebas que deben ser una ayuda se convierten en este caso en un estorbo.

Documento 1

Pág. 42

Versión 1.00

REFACTORING

8. Recomendaciones

- No hay que escribir muchos comentarios en el código. Con demasiados comentarios se

obtiene lo contrario a lo deseado es decir, ofuscación en lugar de claridad y un esfuerzo y tiempo extra por parte del desarrollador (los comentarios hay que mantenerlos junto con el código). Por eso no es bueno abusar de los comentarios.

- Las partes más complejas del código (por ejemplo en un algoritmo, una compleja

operación matemática, un tipo complejo de datos, etc.) que no sean triviales a simple vista deberían llevar un mínimo de comentarios para ayudar a su comprensión y entendimiento puesto que la refactorización por si sola no da la suficiente información con los nombres de funciones, variables, métodos, clases, etc.

- Refactorizar, es decir, hacer el código más limpio, claro, manejable y mantenible

(mejorarlo a grandes rasgos) debería ser obligatorio cada vez que se escribe, rescribe o se mantiene código.

- Cada refactorización que realicemos debe estar justificada. Sólo debemos refactorizar

cuando identifiquemos código mal estructurado o diseños que supongan un riesgo para la futura evolución de nuestro sistema.

- La Refactorización no es un proceso que podemos aislar como una tarea. Es necesario

que lo incluyamos como una actividad que realizaremos cuando estemos desarrollando.

- La restructuración no sólo se da en código, sino en todo el proceso de desarrollo de software: datos, diseño externo, documentación.

- Por definición, los objetos tienen propiedades/características/atributos (variables) que

son propias y que no deben de ser modificables por otros, incluso objetos del mismo tipo.

Documento 1

Pág. 43

Versión 1.00

9. Conclusiones

REFACTORING

1- La refactorización hace el código muchísimo más legible y claro (eso es indudable) y añadiendo las pruebas unitarias tenemos incluso una mínima documentación (y, por supuesto, validación).

2- Refactorizar es realizar modificaciones en el código con el objetivo de mejorar su estructura interna, sin alterar su comportamiento externo.

3- El desarrollo dirigido por pruebas incluye de forma natural la refactorización continua, es lo que se conoce como TDD (Test Driven Development), práctica en la que se hace la prueba, se añade la funcionalidad necesaria para satisfacerla, se generaliza la prueba y se refactoriza.

4- Normalmente desarrollamos nuestros sistemas de software a marchas forzadas, apremiados por los plazos de entrega, lo cual acaba generando un código desordenado.

5- El problema de abordar una refactorización es que supone un esfuerzo que no se ve compensado por ninguna nueva funcionalidad y por ese motivo muchas veces es complicado de justificar.

6- La refactorización de códigos no es una técnica para encontrar y/o corregir errores.

7- El tema de Refactoring esta inmaduro:

Falta de documentación escrita.

Falta y mejora de herramienta.

Documento 1

Pág. 44

Versión 1.00

REFACTORING

10. Bibliografía

[1]. Kerievsky, Joshua (2004). Refactoring to Patterns. Addison Wesley.

[2]. Martin Fowler, Kent Beck, John Brant y William Opdyke, Refactoring: Improving the Design of Existing Code, Addison-Wesley, 1999.

[3]. Pérez Jesús, Ferrer Jorge Refactorización en la práctica: peligros y soluciones

Documento 1

Pág. 45

Versión 1.00