2011-01-16 20 views
7

Nella mia domanda ho 3 parti principali:Linking: Statico vs dinamico

  • Exe: un file eseguibile
  • Lib_A: una biblioteca contiene una classe Singleton e una classe di base per alcuni calcoli da utilizzare in Singleton classe
  • Lib_B: una biblioteca contiene un certo numero di classi derivate dalla base in Lib_A

la ragione per cui ho le classi derivate in Lib_B è, vorrei compilare Lib_B in runtime da Exe. Ho bisogno di generare classi derivate durante i calcoli senza terminare l'intero sistema. Questo è troppo importante per me. Ciò significa che inizialmente potrei dire che Lib_B1 è stato caricato dinamicamente, inoltre posso compilare altre versioni di Lib_B come Lib_B2, Lib_B3, Lib_B4 ecc. E caricarle anche dinamicamente. Tutte le librerie Lib_Bx avranno funzioni di entry point per esportare le classi al loro interno.

in modo da prendere i seguenti fatti in considerazione:

  • In fase di esecuzione ci saranno vari numero di file che condividono lo stesso Lib_A.
  • L'applicazione deve essere eseguita in Windows e Linux. Quindi la cross-platformness parziale è un problema.
  • ho intenzione di utilizzare alcune librerie come TBB, Boost, Qt che può avere le proprie librerie come tbb.dll ecc

Quali sono i pro ei contro di statico o dinamico che collega di Lib_A sia contro Exe e Lib_Bx's? Come possono influire la perfomance, le dimensioni del sistema, ecc.? Ci sono situazioni pericolose o difficili che posso scoprire oltre per ogni sistema operativo ho bisogno di usare lo stesso compilatore per Exe, Lib_A e Lib_Bx.

Il design dell'intero sistema è un problema molto difficile per me, quindi qualsiasi commento sarà apprezzato.

Grazie mille.

risposta

6

Da quanto ho capito della descrizione del progetto, è necessario collegare Lib_A in modo dinamico: se si collega Lib_A staticamente a ciascuna delle librerie condivise Lib_Bx, si duplicheranno x volte il codice Lib_A e le variabili statiche.

Dire, se si dispone di una classe in Lib_A, che hanno la forma:

class BaseKlass 
{ 
    static int instance_count; 
    ... 
}; 

instance_count saranno duplicati in tutte le vostre librerie condivise, quindi l'impossibilità per BaseKlass contare le sue istanze.

che potrebbe eventualmente essere morso da problemi più sottili con tavoli virtuali, o RTTI (dynamic_cast), ecc

Si dovrebbe avere uno sguardo a questo boost.python document che descrive i problemi legati a quello che ho menzionate.

Boost.python consente di creare moduli python (librerie dinamiche) che devono essere caricati nello stesso processo. Ogni modulo python creato con boost.python, se devono comunicare insieme al livello C++ come derivare una classe B in un modulo da una classe A in un altro modulo, dovrebbe collegare dinamicamente con boost.python lib per evitare problemi.

3

Il grande vantaggio del collegamento statico è che non è necessario spedire un sacco di DLL. A meno che non stia pianificando di spedire un eseguibile nudo, penso che sia un problema.

Il collegamento dinamico presenta alcuni grandi vantaggi. Non è necessario ricompilare l'intera applicazione ogni volta che si apporta una modifica, solo le DLL modificate. È possibile distribuire le DLL aggiornate separatamente dal resto dell'applicazione, purché siano compatibili con ABI.

Potrebbe essere più semplice utilizzare lo stesso compilatore su Windows e Linux, ma sicuramente non è necessario utilizzare lo stesso compilatore.

Fintanto che ci si limita alle librerie portatili, la più grande differenza tra Windows e Linux è solitamente il sistema di generazione. Alcuni sviluppatori mantengono sistemi di compilazione completamente separati, ma ci sono molti sistemi di compilazione multipiattaforma come cmake.

+0

Bene, voglio utilizzare il compilatore MSVC++ in Windows e il compilatore Intel C++ in Linux. Penso che entrambi generino un codice ottimizzato meglio di GCC. L'applicazione è solo per uso mio. Non sono disposto a venderlo. –

+0

@sad_man: hai intenzione di ottenere i diritti di ridistribuzione per VC e ICC? Buona fortuna. – ephemient

+0

@ephermient: per il momento non distingo la mia domanda. Ma se lo venderò in futuro, ovviamente il cliente fornirà la propria copia del compilatore. So che non suona bene ma questo è un trucco per ottenere la velocità del codice binario compilato. Per ora sto bene con VC e ICC. Nel peggiore dei casi posso distribuire l'applicazione con GCC giusto? :) –

2

Si desidera creare un nuovo runtime delle classi? C++ non è pensato per funzionare in questo modo. Le classi C++ sono statiche e dovrebbero esistere tutte in fase di compilazione. Le librerie condivise e caricabili dinamicamente non sono pensate per risolvere il problema.

La soluzione più semplice potrebbe essere incorporare un interprete di un linguaggio che ha tipi dinamici (come Lua per esempio) e scrivere gli oggetti dinamici di runtime in esso.

Se si desidera realmente interagire con i moduli compilati in fase di esecuzione in modo indipendente dalla piattaforma, è consigliabile utilizzare un'interfaccia neutra rispetto alla lingua e alla piattaforma come CORBA. Quindi le cose compilate ed eseguite sulla tua Linux box e Windows box possono interagire tra loro e compilare nuovi membri per unirsi alla gang.

+0

Ma allora potrei non beneficiare della velocità e della flessibilità del C++. –

+0

La velocità di qualsiasi applicazione proviene principalmente dalle alte capacità degli sviluppatori.Il codice generato dal runtime dell'input dell'utente non dovrebbe essere considerato efficiente, ma potrebbe essere utile laddove l'efficienza non è necessaria come per la prototipazione. Quindi ho suggerito di usare qualche interprete di script. –

+0

Sì Il codice generato dal runtime dell'input dell'utente non dovrebbe essere efficiente, ma il codice binario compilato dal tempo di esecuzione dell'input dell'utente dovrebbe essere molto più veloce del codice da un interprete di script. –

0

In linea di principio tutto ciò è possibile se tutte e tre sono DLL: è possibile attivare il compilatore dalla propria app e quindi caricare dinamicamente la nuova DLL. Questo è proprio come qualsiasi altra architettura di plugin (considerate le DLL di Lib_Bx come plugin).

Mi chiedevo se questo è un approccio saggio. Hai bisogno della massima flessibilità di un compilatore C++ per la tua soluzione? Hai profilato diversi modi per risolvere il problema? Se stai facendo un'elaborazione numerica, qualcosa come OpenCL potrebbe essere un approccio migliore?