2015-09-03 40 views
5

Costruendo un costruttore privato, possiamo evitare di creare classi di istanza da qualsiasi luogo al di fuori. e rendendo la finale di classe, nessun'altra classe può estenderla. Perché è necessario che la classe Util abbia il costruttore private e la classe final?È obbligatorio che la classe di utilità sia un costruttore definitivo e privato?

+1

Perché pensi che sia obbligatorio? Hai una fonte affidabile che dice che è necessaria? – csmckelvey

+0

Pensa a cosa non puoi fare con una classe che è 'finale' e cosa non puoi fare con una classe che ha un costruttore' private'. –

+0

@SubodhJoshi: ora, con parole tue, spiega cosa pensi di fare una modifica finale della classe ad esso. – Stultuske

risposta

4

Questo non è un mandato dal punto di vista funzionale o Java complicazione o runtime. Tuttavia, il suo standard di codifica accettato dalla più ampia comunità. Anche molti strumenti di revisione del codice statico come checkstyle e molti altri controlli che tali classi hanno seguito questa covention.

Perché questa convenzione è seguita, è già stata spiegata in altre risposte e anche l'OP lo ha coperto.

Mi piace spiegarlo un po 'oltre, principalmente le classi di utilità hanno i metodi/le funzioni che sono indipendenti dall'istanza dell'oggetto. Si tratta di tipi di funzioni aggregate. Poiché dipendono solo dai parametri per i valori di ritorno e non sono associati alle variabili di classe della classe di utilità. Quindi, per lo più queste funzioni/metodi sono mantenuti statici. Di conseguenza, le classi di utilità sono idealmente classi con tutti i metodi statici. Quindi, qualsiasi programmatore che chiama questi metodi non ha bisogno di istanziare questa classe. Tuttavia, alcuni robo-coder (potrebbero avere meno esperienza o interesse) tenderanno a creare oggetti come credono di aver bisogno prima di chiamare il suo metodo. Per evitare che la creazione di oggetti, abbiamo 3 opzioni: -

  1. Mantieni educare le persone non un'istanza. (Nessuna persona sana di mente può continuare a farlo.)
  2. Contrassegna la classe come astratta: - Ancora una volta i robo-codificatori non creeranno l'oggetto. Tuttavia, le revisioni e la più ampia comunità java sosterranno che la marcatura astratta significa che qualcuno deve estenderlo. Quindi, anche questa non è una buona opzione.
  3. Costruttore privato: - Protetto consentirà nuovamente alla classe figlia di creare oggetti.

Ora, ancora una volta, se qualcuno vuole aggiungere nuovo metodo per alcune funzionalità a questi classe di utilità, che non hanno bisogno di estenderlo, egli può aggiungere nuovo metodo come ogni metodo è indepenent e nessuna possibilità di rompere altre funzionalità . Quindi, non c'è bisogno di sovrascriverlo. E inoltre non hai intenzione di istiantare, quindi devi sottoclassi. Meglio segnare la finale.

In sintesi, la creazione di oggetti di classi di utilità non ha senso. Quindi i costruttori dovrebbero essere privati. E tu non vuoi mai scavalcarlo, quindi contrassegnalo come finale.

+1

Grazie Per Spiegazione –

5

Non è necessario, ma è conveniente. Una classe di utilità è solo un detentore di spazi dei nomi di funzioni correlate e non è pensata per essere istanziata o sottoclassata. In questo modo impedire l'istanziazione e l'estensione invia un messaggio corretto all'utente della classe.

+2

Congratulazioni per 100k :) –

+0

Grazie, kocko :) –

+0

Quindi significa solo per comodità nient'altro? –

-1

Di default questo tipo di classe normalmente viene utilizzato per funzioni di aggregazione che fanno diverso questa, in questo caso non abbiamo bisogno di creare un nuovo oggetto

+1

Potresti per favore elaborare più la tua risposta aggiungendo un po 'più di descrizione della soluzione che fornisci? – abarisone

0

C'è una distinzione importante tra il linguaggio Java e il Java Runtime.

Quando la classe Java viene compilato in bytecode, non esiste il concetto di restrizione di accesso, public, package, protected, private sono equivalenti. È sempre possibile tramite la riflessione o la manipolazione del codice by per richiamare il costruttore private, quindi jvm non può fare affidamento su tale abilità.

final d'altra parte, è qualcosa che persiste attraverso il bytecode e le garanzie fornite possono essere utilizzate da javac per generare un codice bytecode più efficiente e da jvm per generare istruzioni di macchina più efficienti.

La maggior parte delle ottimizzazioni abilitate non sono più rilevanti, poiché jvm ora applica le stesse ottimizzazioni a tutte le classi monomorfiche in fase di esecuzione, e queste erano sempre le più importanti.

+0

Grazie Per Spiegazione –

+1

Molte di queste affermazioni sono errate o non si applicano alle classi di utilità. 1. 'invokevirtual' fallirà se la restrizione di accesso lo vieta. 2. Il bytecode di una chiamata riflessa non assomiglia a una chiamata non riflessiva. 3. 'private' ha un effetto sul bytecode, opposto a' final' (si può usare 'invokespecial'). I metodi definitivi pubblici sono chiamati dall'esterno usando 'invokevirtual'. 4. 'final' su una classe non ha alcun effetto sulle chiamate al metodo statico. –