Domanda

Come una persona che ama seguire le best practice,

Se corro metriche del codice (fare clic destro sul nome del progetto in Esplora soluzioni e selezionare "Calcola il codice Metrics" - Visual Studio 2010) su:

    public static string GetFormFactor(int number)
    {
        string formFactor = string.Empty;
        switch (number)
        {
            case 1:
                formFactor = "Other";
                break;

            case 2:
                formFactor = "SIP";
                break;

            case 3:
                formFactor = "DIP";
                break;

            case 4:
                formFactor = "ZIP";
                break;

            case 5:
                formFactor = "SOJ";
                break;
        }

        return formFactor;
    }

mi dà un indice di manutenibilità del 61

(naturalmente questo è insignificante se hai solo questo, ma se si utilizza un programma di utilità come la filosofia di classe whos sta facendo cose del genere, la classe di utilità avrà l'indice di manutenibilità molto peggio ..)

Che cosa è la soluzione per questo?

È stato utile?

Soluzione

Prima di tutto: 61 è considerato il codice mantenibile. Per l'indice manutenibilità, 100 è molto facile da mantenere il codice, mentre 0 è difficile da mantenere.

  • 0-9 = difficile da mantenere
  • 10-19 = moderata per mantenere
  • 20-100 = buono per mantenere

L'indice Maintainability si basa su tre metriche del codice: Vale a dire la Halstead Volumen, la complessità ciclomatica e righe di codice e sulla base della seguente formula :

  

MAX (0, (171 - 5.2 * ln (Halstead   Volume) - 0,23 * (Cyclomatic   Complessità) - 16,2 * ln (Linee di   Codice)) * 100/171)

In realtà, nel tuo esempio la causa principale per il basso valore dell'Indice manutenibilità è la complessità ciclomatica. Questa metrica viene calcolata sulla base dei vari percorsi di esecuzione nel codice. Purtroppo, la metrica non necessariamente si allineano con "leggibilità umana" di codice.

Gli esempi come il risultato del codice di valori di indice molto bassi (ricordate, mezzi inferiori più difficile da mantenere), ma in realtà sono molto facili da leggere. Questo è comune quando si utilizza complessità ciclomatica per valutare il codice.

Immaginate codice che dispone di un interruttore-blocco per i giorni (lun-dom) più un interruttore-blocco per mesi (gennaio-dicembre). Questo codice sarà molto leggibile e gestibile, ma si tradurrà in un enorme complessità ciclomatica e quindi in un bassissimo indice Maintainability in Visual Studio 2010.

Questo è un fatto ben noto sulla metrica e dovrebbe essere considerato se il codice viene giudicato sulla base dei dati. Piuttosto che guardare il numero assoluto, le figure devono essere monitorati nel corso del tempo per capire come un indicatore per il cambio del codice. Per esempio. se l'indice Maintainability era sempre al 100 e improvvisamente scese a 10 si dovrebbe ispezionare il cambiamento che ha causato questo.

Altri suggerimenti

L'indice manutenibilità potrebbe essere più alto a causa della mancanza di espandibilità nel metodo che si sceglie per la vostra soluzione.

La soluzione corretta (Mark Simpson toccato sopra) è quella che può essere espansa per utilizzare un nuovo fattore di forma senza il codice essere ricostruito - dichiarazioni switch / case in codice sono sempre un segno che il design OO è stato dimenticato e deve sempre essere visto come un odore di codice cattivo.

Personalmente, vorrei implementare ...

interface IFormFactor
{
    // some methods
}

class SipFormFactor : IFormFactor...

class DipFormFactor : IFormFactor...

Etc.

... e hanno i metodi sull'interfaccia fornire la funzionalità desiderata -. Si può pensare ad esso [Credo] come simile a pattern GoF Command

In questo modo i metodi di livello superiore può essere solo ...

MyMethod(IFormFactor factor)
{
    // some logic...

    factor.DoSomething();

    // some more logic...
}

... e si può venire in un secondo momento e introdurre un nuovo fattore di forma senza dover modificare il codice come si farebbe con la clausola interruttore hard-coded. Troverete anche questo approccio si presta facilmente a TDD (si dovrebbe finire con questo se si sta facendo TDD correttamente) come è facile per beffardo.

So che questa risposta è molto in ritardo, ma mi interessava che nessuno ha messo ancora la soluzione dizionario. Ho scoperto che quando si tratta di enormi istruzioni switch che sono orientati ai dati come questo, è spesso più leggibile per comprimere la switch-case in un dizionario.

public static readonly IDictionary<int, string> Factors = new Dictionary<int, string> {
   { 1, "Other" },
   { 2, "SIP" },
   { 3, "DIP" },
   { 4, "ZIP" },
   { 5, "SOJ" }
};

public static string GetFormFactor2(int number)
{
   string formFactor = string.Empty;
   if (Factors.ContainsKey(number)) formFactor = Factors[number];
   return formFactor;
}

Questo vi dà un indice di manutenibilità del 74 - leggermente inferiore rispetto alla soluzione a causa della serie di classe accoppiare ad un dizionario, ma sento che è più generale perché funziona per qualsiasi numero di tipi che normalmente accendere. Come la soluzione di array, scale molto bene e rimuove un sacco di codice ripetitivo.

In generale, utilizzando un approccio basato sui dati può aiutare il vostro codice per essere più chiaro, perché separa i pezzi importanti (in questo caso, di una condizione e di conseguenza) dal cruft (in questo caso, lo switch-case) .

Due cose vengono in mente:

Usa un enum per sposare la descrizione e il valore

public enum FormFactor
{
    Other = 1,
    SIP = 2,
    etc.
}

Usa una classe o struct per rappresentare ogni fattore di forma

public class FormFactor 
{
    public int Index { get; private set; }
    public string Description { get; private set; }

    public FormFactor(int index, string description)
    {
        // do validation and assign properties
    }
}

mi piacerebbe farlo in questo modo e dimenticare l'indice Manutenibilità:

public static string GetFormFactor(int number)
{
    switch (number)
    {
        case 1: return "Other";
        case 2: return "SIP";
        case 3: return "DIP";
        case 4: return "ZIP";
        case 5: return "SOJ";
    }

    return number.ToString();
}

IMHO facile da leggere e facile da cambiare.

Non so quanto è importante, ma il seguente ottiene un 76:

private static string[] _formFactors = new[] { null, "Other","SIP","DIP", "ZIP", "SOJ"};
public static string GetFormFactor2(int number)
{
    if (number < 1 || number > _formFactors.Length)
    {
        throw new ArgumentOutOfRangeException("number");
    }

    return _formFactors[number];
}

Chiaramente per me la Enum metodo è il più mantenibile in quanto non comporta stringhe hard-coded quindi non errore di battitura problema e in fase di compilazione controllo della sintassi. Solo restrizioni sono regole di denominazione.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top