Domanda

A Resharper piace sottolineare più funzioni per pagina asp.net che potrebbero essere rese statiche. Mi aiuta se li faccio statici? Devo renderli statici e spostarli in una classe di utilità?

È stato utile?

Soluzione

Metodi statici rispetto ai metodi di istanza
10.2.5 Membri statici e di istanza del C # La specifica della lingua spiega la differenza. In generale, i metodi statici possono fornire un miglioramento delle prestazioni molto ridotto rispetto ai metodi di istanza, ma solo in situazioni alquanto estreme (vedere questa risposta per qualche dettaglio in più).

Regola CA1822 negli stati FxCop o Analisi codice:

  

" Dopo [contrassegnare i membri come statici], il compilatore emetterà siti di chiamata non virtuali a questi membri che impediranno un controllo a   runtime per ogni chiamata che assicura che sia il puntatore dell'oggetto corrente   non nullo. Ciò può comportare un aumento delle prestazioni misurabile per   codice sensibile alle prestazioni. In alcuni casi, il mancato accesso a   l'attuale istanza dell'oggetto rappresenta un problema di correttezza. "

Classe di utilità
Non dovresti spostarli in una classe di utilità a meno che non abbia senso nel tuo progetto. Se il metodo statico si riferisce a un tipo particolare, come un metodo ToRadians (doppi gradi) si riferisce a una classe che rappresenta gli angoli, ha senso che quel metodo esista come membro statico di quel tipo (nota, questo è un esempio contorto ai fini della dimostrazione).

Altri suggerimenti

A mio avviso, prestazioni, inquinamento dello spazio dei nomi, ecc. sono tutti secondari. Chiediti cosa è logico. Il metodo funziona logicamente su un'istanza del tipo o è correlato al tipo stesso? Se è quest'ultimo, rendilo un metodo statico. Spostalo in una classe di utilità solo se è correlato a un tipo che non è sotto il tuo controllo.

A volte ci sono metodi che agiscono logicamente su un'istanza ma non usano nessuno stato dell'istanza . Ad esempio, se stavi costruendo un file system e avessi ottenuto il concetto di directory, ma non lo avessi ancora implementato, potresti scrivere una proprietà che restituisca il tipo di oggetto del file system e sarebbe sempre " file di " - ma è logicamente correlato all'istanza e quindi dovrebbe essere un metodo di istanza. Ciò è importante anche se si desidera rendere virtuale il metodo: l'implementazione particolare potrebbe non richiedere stato, ma le classi derivate potrebbero. (Ad esempio, chiedendo a una raccolta se è di sola lettura - potresti non aver ancora implementato un modulo di sola lettura di quella raccolta, ma è chiaramente una proprietà della raccolta stessa, non del tipo.)

Contrassegnare un metodo come statico all'interno di una classe rende ovvio che non utilizza alcun membro di istanza, che può essere utile sapere quando si scorre il codice.

Non devi necessariamente spostarlo in un'altra classe a meno che non sia pensato per essere condiviso da un'altra classe che è altrettanto strettamente associata, dal punto di vista concettuale.

Sono sicuro che questo non sta accadendo nel tuo caso, ma un "cattivo odore" Ho visto in alcuni codici che ho dovuto soffrire per aver usato un sacco di metodi statici.

Sfortunatamente, erano metodi statici che presupponevano un particolare stato dell'applicazione. (perché certo, avremo un solo utente per applicazione! Perché non fare in modo che la classe User tenga traccia di ciò nelle variabili statiche?) Erano modi glorificati per accedere alle variabili globali. Avevano anche costruttori statici (!), Che sono quasi sempre una cattiva idea. (So ??che ci sono un paio di eccezioni ragionevoli).

Tuttavia, i metodi statici sono piuttosto utili quando determinano la logica del dominio che in realtà non dipende dallo stato di un'istanza dell'oggetto. Possono rendere il tuo codice molto più leggibile.

Assicurati solo di metterli nel posto giusto. I metodi statici manipolano in modo intrusivo lo stato interno di altri oggetti? Si può sostenere che il loro comportamento appartiene invece a una di quelle classi? Se non stai separando correttamente le preoccupazioni, potresti avere mal di testa in seguito.

È interessante leggere:

http://thecuttingledge.com/?p=57

ReSharper non ti sta suggerendo di rendere statico il tuo metodo. Dovresti chiederti perché quel metodo è in quella classe invece di, diciamo, una delle classi che appare nella sua firma ...

ma ecco cosa dice documentaion resharper: http://confluence.jetbrains.net/display/ReSharper/Member + + può essere fatta + + static

Solo per aggiungere a @Jason True's risposta , è importante rendersi conto che mettere semplicemente "statico" su un metodo non garantisce che il metodo sia "puro". Sarà apolide rispetto alla classe in cui viene dichiarato, ma potrebbe anche accedere ad altri oggetti "statici" con stato (configurazione dell'applicazione ecc.), Questo potrebbe non essere sempre una cosa negativa, ma uno dei motivi per cui Personalmente tendo a preferire metodi statici quando posso che se sono puri, puoi testarli e ragionarli in modo isolato, senza doversi preoccupare dello stato circostante.

Dovresti fare ciò che è più leggibile e intuitivo in un determinato scenario.

L'argomento delle prestazioni non è valido tranne nelle situazioni più estreme poiché l'unica cosa che sta realmente accadendo è che un parametro aggiuntivo ( this ) viene inserito nello stack per i metodi di esempio.

Per la logica complessa all'interno di una classe, ho trovato utili metodi statici privati ??nella creazione di una logica isolata, in cui gli input dell'istanza sono chiaramente definiti nella firma del metodo e non possono verificarsi effetti collaterali dell'istanza. Tutte le uscite devono essere tramite valore di ritorno o parametri out / ref. Abbattere la logica complessa in blocchi di codice privi di effetti collaterali può migliorare la leggibilità del codice e la fiducia del team di sviluppo in esso.

D'altra parte può portare a una classe inquinata da una proliferazione di metodi di utilità. Come al solito, la denominazione logica, la documentazione e l'applicazione coerente delle convenzioni di codifica del team possono alleviarlo.

ReSharper non controlla la logica. Verifica solo se il metodo utilizza membri dell'istanza. Se il metodo è privato e chiamato solo da (forse solo uno) metodi di istanza, questo è un segno per lasciarlo un metodo di istanza.

Se le funzioni sono condivise su più pagine, è anche possibile inserirle in una classe di pagine di base e quindi far sì che tutte le pagine asp.net utilizzino quella funzionalità ereditata da essa (e le funzioni potrebbero anche essere statiche).

Rendere statico un metodo significa che puoi chiamare il metodo dall'esterno della classe senza prima creare un'istanza di quella classe. Ciò è utile quando si lavora con oggetti o componenti aggiuntivi di fornitori di terze parti. Immagina di dover prima creare un oggetto Console " con " prima di chiamare con.Writeline ();

Aiuta a controllare l'inquinamento dello spazio dei nomi.

Solo il mio supporto: l'aggiunta di tutti i metodi statici condivisi a una classe di utilità consente di aggiungere

using static className; 

alle tue istruzioni using, che rendono il codice più veloce da digitare e più facile da leggere. Ad esempio, ho un gran numero di quelle che sarebbero chiamate "variabili globali" in qualche codice ho ereditato. Invece di creare variabili globali in una classe che era una classe di istanza, le ho impostate tutte come proprietà statiche di una classe globale. Fa il lavoro, anche se in modo disordinato, e posso semplicemente fare riferimento alle proprietà per nome perché ho già lo spazio dei nomi statico a cui si fa riferimento.

Non ho idea se questa è una buona pratica o no. Ho così tanto da imparare su C # 4/5 e così tanto codice legacy da refactoring che sto solo cercando di lasciarmi guidare dai suggerimenti di Roselyn.

Joey

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