2009-05-23 16 views
5

Sono abbastanza nuovo in C++ e ho visto un mucchio di codice con definizioni di metodo nei file di intestazione e non dichiarano il file di intestazione come un classe. Qualcuno può spiegarmi perché e quando faresti qualcosa del genere. È una cattiva pratica?Quando utilizzare i file di intestazione che non dichiarano una classe ma hanno definizioni di funzione

Grazie in anticipo!

+0

intendi intestazioni senza classe? non sei sicuro di cosa intendi con "che non dichiarano una classe", a causa dei diversi usi di "dichiarare una classe" nella comunità SO. –

+0

Sì, intendo un'intestazione senza classe, non ero sicuro di come spiegarlo. Fondamentalmente un file di intestazione che ha solo un mucchio di definizioni di funzioni. –

risposta

11

È una cattiva pratica?

Non in generale. Ci sono molte librerie che sono header only, nel senso che vengono spedite solo file di intestazione. Questo può essere essere visto come un'alternativa leggera alle librerie compilate. Ancora più importante, tuttavia, è possibile che non possa utilizzare unità di compilazione precompilate separate: i modelli devono essere specializzati nella stessa unità di compilazione in cui vengono dichiarati. Questo può sembrare arcano ma ha una semplice conseguenza:

I modelli di funzione (e di classe) non possono essere definiti all'interno di file cpp e utilizzati altrove; invece, sono avere da definire direttamente nei file di intestazione (con alcune eccezioni degne di nota).

Inoltre, le classi in C++ sono puramente facoltative - mentre l'utente può essere orientato agli oggetti del programma in C++, un sacco di buon codice no. Classi integrano gli algoritmi in C++, non il contrario.

-1

In C++, le funzioni non devono essere membri delle classi.

+1

Non che la mia risposta fosse buona, ma non vedo come questa risposta "Qualcuno può spiegarmi perché e quando faresti qualcosa di simile? È una cattiva pratica?". Ovviamente è legale visto che l'ha visto nel codice di lavoro. – Uri

1

Un file H è semplicemente un modo di includere un gruppo di dichiarazioni. Molte cose in C++ sono dichiarazioni utili, tra cui classi, tipi, costanti, funzioni globali, ecc.

C++ ha una sfaccettatura orientata agli oggetti. La maggior parte delle lingue OO affronta la questione di dove gestire le operazioni che non si basano sullo stato dell'oggetto e non hanno effettivamente bisogno dell'oggetto.

In alcune lingue, come Java, le restrizioni del linguaggio impongono che tutto sia in una classe, quindi tutto diventa una funzione membro statico (ad esempio, classi con utilità matematiche o algoritmi).

In C++, per mantenere la compatibilità con C, è possibile dichiarare funzioni in stile C standalone o utilizzare lo stile Java di membri statici. La mia opinione personale è che è meglio, quando possibile, utilizzare lo stile OO e organizzare le operazioni attorno a un concetto centrale.

Tuttavia, C++ fornisce le funzionalità dei namespace e spesso viene utilizzato nello stesso modo in cui una classe verrebbe utilizzata in tali situazioni - per raggruppare un gruppo di articoli autonomi in cui ogni elemento è preceduto dal nome "namespace". Come altri sottolineano, molte funzioni della libreria standard C++ si trovano in questo modo. La mia opinione è che questo è molto simile all'utilizzo di una classe in Java. Tuttavia, altri sostengono che Java utilizza le classi perché non ha spazi dei nomi. Fintanto che usi l'una o l'altra (piuttosto che una funzione autonoma non assegnata allo stesso nome), in genere starai bene.

+1

Come al solito, le tue osservazioni sulla pratica del C++ sono sbagliate. Il C++ non "preferisce" le classi. –

+4

@Neil: C++ viene in genere insegnato per la programmazione orientata agli oggetti, specialmente ora che C stesso è stato aggiornato con un sacco di cose per renderlo più utilizzabile. Continuo a sostenere che OOP è preferibile. Ma davvero non devi essere un tale idiota. – Uri

+2

Neil, mi aspetto che Uri abbia inteso che i programmatori C++ * preferiscono le classi, il che è vero nella mia esperienza (anche se soggettiva). – ChrisW

4

Non è una cattiva pratica. Il bello del C++ è che ti permette di programmare in molti stili. Ciò conferisce al linguaggio una grande flessibilità e utilità, ma forse rende più complicato da imparare rispetto ad altri linguaggi che ti obbligano a scrivere codice in uno stile particolare.

Se si dispone di un programma di dimensioni ridotte, è possibile scriverlo in un'unica funzione, possibilmente utilizzando un paio di goto per il flusso di codice.

Quando si aumenta, la suddivisione del codice in funzioni consente di organizzare le cose.

Più grande ancora, e le classi sono generalmente un buon modo per raggruppare le funzioni correlate che funzionano su un determinato insieme di dati.

Più grande ancora, i namespace aiutano.

A volte, tuttavia, è più semplice scrivere una funzione per fare qualcosa. Questo è spesso il caso in cui si scrive una funzione che funziona solo su tipi primitivi (come int). int non ha una classe, quindi se vuoi scrivere una funzione printInt(), potresti renderla indipendente. Inoltre, se una funzione funziona su oggetti di più classi, ma in realtà non appartiene a una classe e non all'altra, ciò potrebbe avere senso come funzione autonoma. Questo accade molto quando scrivi operatori come definire meno di così da poter confrontare oggetti di due classi diverse. Oppure, se una funzione può essere scritta in termini di metodi pubblici di classi e non ha bisogno di accedere direttamente ai dati della classe, alcune persone preferiscono scriverle come una funzione autonoma.

Ma, davvero, la scelta è vostra. Qualunque sia la cosa più semplice da fare per risolvere il tuo problema è la cosa migliore.

È possibile avviare un programma come solo alcune funzioni, quindi decidere in seguito se alcune sono correlate e riordinarle in una classe. Ma se le altre funzioni autonome non rientrano naturalmente in una classe, non è necessario forzarle in una classe.

0

Sono abbastanza nuovo per C++ e ho visto un gruppo di codice che ha definizioni di metodo nei file di intestazione e non dichiarano il file di intestazione come una classe.

Consente di chiarire le cose.

definizioni dei metodi nei file di intestazione

Questo significa che qualcosa di simile: file "A.h":

class A { 
void method(){/*blah blah*/} //definition of a method 
}; 

E 'questo quello che volevi dire?

In seguito si dice "dichiarare il file di intestazione". Non esiste un meccanismo per DICHIARARE un file in C++. Un file può essere INCLUSO con lo #include "filename.h". Se lo fai, i contenuti del file di intestazione saranno copiati e incollati ovunque tu abbia la linea sopra prima che qualcosa venga compilato.

Quindi si intende che tutte le definizioni sono nella definizione di classe (non in qualsiasi parte in A.h FILE, ma in particolare nella classe A, che è limitata da 'classe A {' e '};'). L'implicazione di avere la definizione del metodo nella definizione della classe è che il metodo sarà 'in linea' (questa è la parola chiave C++), il che significa che il corpo del metodo verrà incollato ogni volta che vi è una chiamata.Si tratta di:

  • bene, perché il meccanismo di chiamata di funzione non è più rallenta l'esecuzione
  • male se la funzione è più lungo di una breve dichiarazione, perché la dimensione del codice eseguibile cresce male

Le cose sono diverse per i modelli come qualcuno sopra detto, ma per loro c'è un modo di definire metodi tali da non essere in linea, ma ancora nel file di intestazione (devono essere nelle intestazioni). Queste definizioni devono comunque essere al di fuori della definizione della classe.

Problemi correlati