Perché qualcuno dovrebbe dichiarare protetto un costruttore? So che i costruttori sono dichiarati privati allo scopo di non consentire la loro creazione in pila.Quali sono gli usi pratici di un costruttore protetto?
risposta
Quando una classe è (intesa come) una classe astratta, un costruttore protetto ha esattamente ragione. In questa situazione non vuoi che gli oggetti siano istanziati dalla classe ma usino solo per ereditarli.
Esistono altri casi di utilizzo, ad esempio quando un determinato insieme di parametri di costruzione deve essere limitato alle classi derivate.
un uso potrebbe essere modelli di fabbrica
Un costruttore protetto significa che solo i membri derivati possono costruire le istanze della classe (e le istanze derivate) che utilizzano tale costruttore. Questo suona un po 'pollo-e-uovo, ma a volte è utile quando si implementano le fabbriche di classi.
Tecnicamente, questo si applica solo se TUTTI i sensori sono protetti. Le classi di amici – MSalters
possono anche chiamare il costruttore protetto (non solo le classi derivate). –
...e l'uso di una classe friend che chiama il costruttore protetto sarebbe nel caso di un oggetto che ha membri che sono costanti (impostati dal costruttore) ma che devono essere pubblici, ma che non devono mai essere impostati da nessun altro accesso pubblico, garantisce che l'oggetto non verrà creato da qualche altra parte e quindi i dati non verranno modificati da nessun'altra parte. – osirisgothra
Per consentire a una sottoclasse di utilizzare un costruttore che non dovrebbe essere accessibile direttamente a un programma di creazione di istantanee.
Si può usare per limitare le classi che potrebbero creare, ad esempio:
class Level
{
private:
Level();
¨Level();
friend class LevelManager;
};
L'unica classe che può creare un'istanza di esso è la classe LevelManager, così saprete sempre che il livello l'istanza viene creata nel LevelManager.
Mentre vero, si tratta di un costruttore privato, non protetto. – David
ahaha scusa, ho letto male. Devo cancellare il mio post? –
I costruttori non pubblici sono utili quando ci sono requisiti di costruzione che non possono essere garantiti unicamente dal costruttore. Ad esempio, se un metodo di inizializzazione deve essere chiamato subito dopo il costruttore, o se l'oggetto deve registrarsi con qualche oggetto contenitore/gestore, questo deve essere fatto al di fuori del costruttore. Limitando l'accesso al costruttore e fornendo solo un metodo di fabbrica, è possibile garantire che qualsiasi istanza ricevuta da un utente soddisfi tutte le sue garanzie. Questo è anche comunemente usato per implementare un Singleton, che è in realtà solo un'altra garanzia della classe (che ci sarà solo una singola istanza).
Il motivo per cui il costruttore è protetto, anziché privato, è lo stesso per rendere qualsiasi altro metodo o campo protetto invece che privato: in modo che possa essere ereditato dai bambini. Forse vuoi un metodo factory, non virtuale virtuale nella classe base, che restituisce riferimenti alle istanze delle classi derivate; le classi derivate ovviamente vogliono l'accesso ai costruttori genitori, ma non si vuole ancora crearli al di fuori della propria fabbrica.
Per i metodi di fabbrica con effetti collaterali.
class mine {
private:
mine() {};
protected:
mine(int id) : m_id(id) {};
int m_id;
static int m_count;
public:
static mine* CreateOneOfMe() {
return mine(m_count++);
}
int GetId() { return m_id; }
};
Questo crea istanze della classe e garantisce che ognuna di esse ha un ID intero incrementale univoco. Si noti che se il costruttore che si desidera utilizzare non è l'impostazione predefinita, è necessario nascondere anche il valore predefinito.
Un costruttore protetto può essere utilizzato per rendere una classe effettivamente astratta quando nessuno dei suoi metodi è puro-virtuale.
Non è abbastanza astratto nel senso del C++ poiché le classi di amici possono ancora usarlo senza sovrascrivere, ma poi dovresti dichiararle.
- 1. Quali sono gli usi pratici del modulo (%) nella programmazione?
- 2. Quali sono gli usi pratici del modello di metodo di fabbrica?
- 3. Quali sono gli usi comuni di UDP?
- 4. Quali sono gli usi del buffer circolare?
- 5. Quali sono gli usi dei generi polimorfici?
- 6. Usi pratici di MethodRental Class?
- 7. Comportamento del costruttore esplicito della copia ed usi pratici
- 8. Quali sono gli usi corretti di @NonNull e @Nullable?
- 9. Quali sono gli usi migliori degli archivi di documenti?
- 10. Quali sono gli usi di iter (callable, sentinel)?
- 11. Quali sono tutti gli usi di '@' in C#?
- 12. Quali sono gli usi del predicato di errore in Prolog?
- 13. Quali sono gli usi popolari e contemporanei di Perl?
- 14. Quali sono gli usi positivi dei moduli in pacchetto OCaml?
- 15. Quali sono gli usi esatti del termine REALM in sicurezza?
- 16. Quali sono alcuni usi interessanti per gli agenti Java?
- 17. Quali sono gli usi positivi della proprietà css `content`?
- 18. Quali sono gli usi del membro get() dalla classe shared_ptr?
- 19. Quali sono gli usi delle funzioni virtuali pure in C++?
- 20. alcuni usi pratici di mem_fn e binding
- 21. Quali sono alcuni usi intelligenti di LINQ?
- 22. jQuery.map - usi pratici per la funzione?
- 23. Usi pratici del livello di Isolamento di Serializzazione?
- 24. Quali sono alcuni usi dei metadati Clojure?
- 25. Cosa sono i campionatori di ombre in OpenGL e quali sono gli usi possibili per loro?
- 26. Quali sono i limiti pratici dei thread per CPU?
- 27. Quali sono gli intrinsechi?
- 28. Quali sono alcuni usi interessanti delle funzioni di ordine superiore?
- 29. Quali sono i limiti pratici al numero di istanze FileSystemWatcher un server in grado di gestire?
- 30. Quali sono gli usi comuni delle variabili di condizione in C++?
+1 Ma non necessariamente deve essere una classe astratta. È spesso il caso però. – ralphtheninja
Non è sufficiente dichiarare una funzione come virtuale pura per la definizione di una classe base? O quanto sopra è in assenza di pura funzione virtuale. Che cos'è un evento di creazione per una classe derivata di una classe astratta? –
@Henk Holterman lo fa di certo - vedere la sezione 10.4 del ++ standard C, dal titolo "classi astratte" –