2011-05-16 5 views
20

Estoy buscando en el FCM métrica como se muestra aquí,¿Por qué la falta de cohesión de los métodos (FCM) Incluir captadores y definidores

http://www.ndepend.com/Metrics.aspx

Así que están diciendo algunas cosas,

1) A class is utterly cohesive if all its methods use all its instance fields 
2) Both static and instance methods are counted, it includes also constructors, properties getters/setters, events add/remove methods 

Si miro a una clase como esta,

public class Assessment 
{ 
    public int StartMetres { get; set; } 
    public int EndMetres { get; set; } 
    public decimal? NumericResponse { get; set; } 
    public string FreeResponse { get; set; } 
    public string Responsetype { get; set; } 
    public string ItemResponseDescription { get; set; } 
    public string StartText { get; set; } 
    public decimal? SummaryWeight { get; set; } 
} 

Obtiene una mala puntuación de 0.94 porque cada getter y setter no accede a 'todos los demás campos de instancia'.

Se calcula como este,

accessAverage - methodCount/1 - methodCount 

(2 - 17)/(1 - 17) = 0.94 (rounded) 

yo no soy la comprensión de esta métrica, ¿por qué debería incluir captadores y definidores? Un getter y un setter siempre accederán a un solo campo de instancia.

+1

Yo diría que la métrica de LCOM debe considerar que las propiedades automáticas sean las mismas que los campos. – Gabe

+3

Lo que pasa con las métricas similares a LCOM es que esa cosa de 'Evaluación', eso no es realmente una clase. Es solo un POCO tonto ("tonto" que tiene un significado específico, no despectivo), una estructura (o registro en el lenguaje parecido a Pascal). No tiene comportamiento (comportamiento típicamente representado por relaciones entre los métodos). Ergo, es no es una verdadera ** clase **. Puede ser desde un POV de lenguaje, pero no desde un POV de dominio (que es lo que realmente le importa). O evito recopilar métricas de LCOM en POJOS o structs, o ignoro los resultados para ellos. LCOM tiene razón, no es una clase. Simplemente usa esa información en consecuencia. –

+1

Quizás porque getters y setters en realidad están reduciendo la cohesión de la clase y deben evitarse en la programación orientada a objetos: http://www.yegor256.com/2014/09/16/getters-and-setters-are-evil. html – yegor256

Respuesta

26

Esto demuestra que todas las métricas de software son defectuosas si lo llevas ciegamente al extremo.

Usted conoce una clase "incohesive" cuando la ve. Por ejemplo:

class HedgeHog_And_AfricanCountry 
{ 

    private HedgeHog _hedgeHog; 
    private Nation _africanNation; 

    public ulong NumberOfQuills { get { return _hedgeHog.NumberOfQuills; } } 
    public int CountOfAntsEatenToday { get { return _hedgeHog.AntsEatenToday.Count(); } } 

    public decimal GrossDomesticProduct { get { return _africanNation.GDP; } } 
    public ulong Population { get { return _africanNation.Population; } } 
} 

Esto es obviamente una clase incohesive, ya que contiene dos piezas de datos que no necesitan ser uno con el otro.

Pero si bien es obvio para nosotros que esta clase es incoherente, ¿cómo se puede obtener un programa de software para determinar la incohesion? ¿Cómo podría decir que la clase anterior es coherente, pero no es así?

class Customer 
{ 
    public string FullName { get; set; } 
    public Address PostalAddress { get; set; } 
} 

La métrica que llevaron a cabo sin duda detecta incohesion, sino que también trae como falsos positivos.

¿Qué pasa si decides que esta métrica es importante? Puede crear una clase "CustomerData" que contenga solo campos y una clase "Customer" que exponga los campos de datos como propiedades.

// This has no methods or getters, so gets a good cohesion value. 
class CustomerData 
{ 
    public string FullName; 
    public Address PostalAddress; 
} 

// All of the getters and methods are on the same object 
class Customer 
{ 
    private CustomerData _customerData; 
    public string FullName { get { return _customerData.FullName; } } 
    // etc 
} 

Pero si estoy jugando a este juego, puedo aplicarlo al ejemplo incohesive así:

class Hedgehog_And_AfricanCountry_Data 
{ 
    public Hedgehog _hedgehog; 
    public AfricanNation _africanNation; 
} 

class Hedgehog_And_AfricanCountry 
{ 
    private Hedgehog_And_AfricanCountry_Data _hedgehogAndAfricanCountryData; 
    // etc; 
} 

Realmente, creo que lo mejor es entender lo que la cohesión es, y por qué se trata de una objetivo que vale la pena, pero también entiendo que una herramienta de software no puede medirlo correctamente.

+1

Puntos muy interesantes. Gracias. – peter

+0

Sin embargo, al pensarlo un poco más, ¿un getter y un setter nunca accederían a un campo de todas formas? ¿O se supone que el valor de la métrica se reduce en las clases donde hay montones de métodos? – peter

+1

Supongo que lo que intento decir es: ¿no deberíamos eliminar los getters y setters? ¿No daría eso resultados más precisos? – peter

Cuestiones relacionadas