Pregunta

La Ley de Demeter indica que solo debe hablar con los objetos que conoce directamente. Es decir, no realice el encadenamiento de métodos para hablar con otros objetos. Cuando lo haces, estás estableciendo enlaces impropios con los objetos intermedios, inadecuadamente acoplamiento tu código a otro código.

Eso es malo.

La solución sería que la clase que usted conoce exponga esencialmente envoltorios simples que delegan la responsabilidad al objeto con el que tiene relación.

Eso es bueno.

Pero, eso parece dar lugar a que la clase tenga un bajo cohesion . Ya no es simplemente responsable de lo que hace precisamente, sino que también cuenta con los delegados que, en cierto sentido, hace que el código sea menos cohesivo al duplicar partes de la interfaz de su objeto relacionado.

Eso es malo.

¿Realmente resulta en una disminución de la cohesión? ¿Es el menor de dos males?

¿Es esta una de esas áreas grises de desarrollo, donde puede debatir dónde está la línea, o existen formas sólidas y basadas en principios para tomar una decisión sobre dónde dibujar la línea y qué criterios puede usar para tomar esa decisión?

¿Fue útil?

Solución

Grady Booch en " Análisis y diseño orientado a objetos " ;:

" La idea de cohesión también proviene del diseño estructurado. En pocas palabras, cohesión mide el grado de conectividad entre los elementos de un solo módulo (y para el diseño orientado a objetos, una sola clase u objeto). La forma menos deseable de cohesión es cohesión coincidente, en la que abstracciones totalmente no relacionadas son arrojados a la misma clase o modulo. Por ejemplo, considere una clase que comprende Las abstracciones de los perros y las naves espaciales, cuyos comportamientos no tienen relación alguna. los La forma más deseable de cohesión es la cohesión funcional, en la que los elementos de una clase o módulo todos trabajan juntos para proporcionar un comportamiento bien delimitado. Por lo tanto, la clase Dog es funcionalmente cohesiva si su semántica abarca el comportamiento. de un perro, el perro entero, y nada más que el perro. "

Subsitute Dog with Customer en lo anterior y podría ser un poco más claro. Por lo tanto, el objetivo es realmente apuntar a la cohesión funcional y alejarse lo más posible de la cohesión coincidente. Dependiendo de sus abstracciones, esto puede ser simple o podría requerir una refactorización.

La cohesión de notas se aplica tanto a un " módulo " que a una sola clase, es decir, un grupo de clases trabajando juntos. Entonces, en este caso, las clases de Clientes y Pedidos aún tienen una cohesión decente porque tienen esta fuerte relación, los clientes crean pedidos, los pedidos pertenecen a los clientes.

Martin Fowler dice que se sentiría más cómodo llamándolo " Suggestion of Demeter " (consulte el artículo Los simulacros no son talones ):

" Los probadores de Mockist hablan más sobre cómo evitar "accidentes de tren": cadenas de métodos de estilo de getThis (). getThat (). getTheOther (). Evitar las cadenas de métodos también se conoce como siguiendo la Ley de Demeter. Si bien las cadenas de métodos son un olor, el problema opuesto de los objetos del hombre medio hinchados con métodos de reenvío es también un olor. (Siempre sentí que me sentiría más cómodo con la Ley de Deméter si se llamara Sugerencia de Deméter .) & Quot;

Eso resume muy bien de dónde vengo: es perfectamente aceptable y, a menudo, es necesario tener un nivel de cohesión más bajo que la adhesión estricta a la ley " podría requerir Evite la cohesión coincidente y apunte a la cohesión funcional, pero no se obsesione con los ajustes necesarios para que se adapte de forma más natural a la abstracción de su diseño.

Otros consejos

Si estás violando la Ley de Demeter al tener

int price = customer.getOrder().getPrice();

la solución no es crear un getOrderPrice () y transformar el código en

int price = customer.getOrderPrice();

pero en su lugar, tenga en cuenta que esto es un codifican el olor y realizan los cambios relevantes que, con suerte, aumentan la cohesión y disminuyen el acoplamiento. Desafortunadamente, no hay una refactorización simple aquí que siempre aplique, pero probablemente debería aplicar decir no preguntar

Creo que puedes haber entendido mal lo que significa la cohesión. Una clase que se implementa en términos de varias otras clases no necesariamente tiene una baja cohesión, siempre que represente un concepto claro y tenga un propósito claro. Por ejemplo, puede tener una class Person , que se implementa en términos de las clases Date (para la fecha de nacimiento), Address y < código> Educación (una lista de las escuelas a las que asistió la persona). Puede proporcionar envoltorios en Persona para obtener el año de nacimiento, la última escuela a la que asistió o el estado donde vive, para evitar exponer el hecho de que Persona es implementado en términos de esas otras clases. Esto reduciría el acoplamiento, pero haría que Person no sea menos cohesivo.

Es un área gris. Estos principios están destinados a ayudarlo en su trabajo, si descubre que está trabajando para ellos (es decir, se están interponiendo en su camino y / o si lo encuentra complica su código), entonces se está ajustando demasiado y necesita para retroceder.

Haz que funcione para ti, no lo hagas.

No sé si esto realmente reduce la cohesión.

La agregación / composición se trata de una clase que utiliza otras clases para cumplir con el contrato que expone a través de sus métodos públicos. La clase no necesita duplicar la interfaz de sus objetos relacionados. En realidad, está ocultando cualquier conocimiento sobre estas clases agregadas del llamador del método.

Para obedecer la ley de Demeter en el caso de niveles múltiples de dependencia de clase, solo necesita aplicar la agregación / composición y una buena encapsulación en cada nivel.

En otras palabras, cada clase tiene una o más dependencias en otras clases, sin embargo, estas son solo dependencias siempre de la clase a la que se hace referencia y no de ningún objeto devuelto desde propiedades / métodos.

En las situaciones en las que parece haber un intercambio entre el acoplamiento y la cohesión, probablemente me pregunte "si alguien más ya hubiera escrito esta lógica, y estuviera buscando un error en ella, ¿dónde buscaría primero? ? " y escribe el código de esa manera.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top