2011-01-24 4 views
7

Sto provando a scrivere un programma in stile funzionale con C il più possibile. Conosco silenziosi compilatori come GCC/Clang do tail, ma non è garantito. C'è qualche opzione per forzare l'ottimizzazione delle chiamate tail sui compilatori? (Ovviamente quando viene chiamato solo alla fine di se stesso)È possibile forzare l'ottimizzazione delle chiamate tail su GCC/Clang?

+4

Il compilatore è probabilmente piuttosto intelligente a questo proposito, fidatevi. Non c'è bisogno di hack * non-portatili *. –

+1

Cosa vuoi che succeda nei casi in cui pensi che l'ottimizzazione della coda dovrebbe verificarsi ma il compilatore non è in grado di farlo (per qualsiasi ragione)? –

+4

@ Michael mi aspettavo un errore di compilazione se l'ottimizzazione forzata delle chiamate tail è impossibile. – Eonil

risposta

4

Clang non esegue alcuna ottimizzazione. C'è un pass LLVM tailcallelim che può fare ciò che vuoi (ma non è garantito). Puoi eseguirlo separatamente con opt.

+0

Qual è l'opzione? Posso avere qualche link per questo? – Eonil

+0

opt è uno strumento da riga di comando fornito con llvm, http://llvm.org/cmds/opt.html –

+3

In alternativa è possibile modificare il driver clang per assicurarsi che venga eseguito questo passaggio in modo esplicito. –

0

In realtà un sacco di compilatori per C lo gestiscono già per te. Come accennato, potresti anche lasciare che il compilatore gestisca la maggior parte di queste cose piuttosto che provare a creare ottimizzazioni che non funzioneranno altrove. Spesso, anche se imposti i flag di ottimizzazione, non troverai alcuna differenza di prestazioni.

1

Una risposta meta:

Ci sono alcune lezioni è utile prendere in consegna in C da linguaggi funzionali: l'uso di piccole funzioni, funzioni d'uso che non mutano né globali o argomenti di input, non abbiate paura di puntatori di funzioni. Ma c'è un limite a ciò che si può ragionevolmente fare qui, e fare affidamento sull'eliminazione di chiamata di coda ('ottimizzazione di coda ' non è proprio il termine giusto) è probabilmente al di là di ciò che è utile. Non è possibile forzare il compilatore a utilizzare questa strategia, e anche se fosse possibile, la risultante C sarebbe estremamente unidiomatica e difficile da leggere per gli altri, incluso il proprio sé futuro.

Utilizzare le lingue per i loro punti di forza. C è buono per alcune cose, quindi usalo per quelli, in buono stile C. Se vuoi diversi punti di forza, o se vuoi usare uno stile funzionale (ottima decisione!), Usa un linguaggio funzionale.

0

Se in realtà è una coda, un ciclo while o un goto non appariranno molto diversi da una chiamata ricorsiva. Basta aggiornare tutte le variabili invece di passarle come parametri. AFAIK questo è l'unico modo multipiattaforma in C per controllare l'utilizzo dello stack a tutti i livelli di ottimizzazione. Può anche essere più leggibile poiché hai una funzione con inizializzazione seguita dal ciclo, che è piuttosto idiomatica. La versione ricorsiva della coda richiede due funzioni, una per l'inizializzazione e una per la parte ricorsiva.