2011-01-24 12 views
7

私はできるだけCで関数型のプログラムを書こうとしています。 私は、GCC/Clangのようなきれいなコンパイラが黙って呼び出し最適化を行うことは知っていますが、それは保証されていません。コンパイラでテールコールの最適化を強制するオプションはありますか? (当然、それはそれ自身の最後に呼び出されたときだけです)GCC/Clangでテールコールの最適化を強制できますか?

+4

コンパイラはこの点ではおそらくスマートですが、信頼してください。ポータブルでないハックの必要はありません。 –

+1

テールの最適化が行われるべきだが、コンパイラが(何らかの理由で)それを行うことができないと思われる場合に、あなたは何をしたいですか? –

+4

@Michael強制的なテールコールの最適化が不可能な場合、私はコンパイル時のエラーが予想されました。 – Eonil

答えて

4

Clangは最適化を一切行っていません。 LLVMパスtailcallelimがありますが、それはあなたが望むことをするかもしれませんが(保証されません)。 optと別々に実行できます。

+0

optとは何ですか?私はそれのための任意のリンクを持つことができますか? – Eonil

+0

optは、llvm、http://llvm.org/cmds/opt.htmlに同梱されているコマンドラインツールです。 –

+3

また、このパスを明示的に実行するために、clangドライバを調整することもできます。 –

0

実際には、C用の多くのコンパイラがこれを処理しています。 eqで述べたように、他の場所では動作しない最適化を作成するのではなく、コンパイラでこれらのほとんどの処理を行うことができます。最適化フラグを設定しても、実際にはパフォーマンスの差はないことがよくあります。

1

メタ答え:

それは関数型言語からCに引き継ぐために便利ですいくつかの教訓があります。小さな関数を使用して、グローバルまたは入力引数のいずれかを変化させません使用機能は、の怯えことはありません関数ポインタ。しかし、あなたがここで合理的にできることには限界があり、テールコールの除去(tail-call 最適化は実際には適切な用語ではありません)に頼っているのはおそらく有用ではありません。コンパイラにこの戦略を強制的に使用させることはできません。たとえできたとしても、結果として得られるCは非常に単調で、将来の自己を含めて他の人にとっては読みにくいでしょう。

強みを発揮する言語を使用します。 C なので、良いCスタイルのものに使用してください。異なる強みが必要な場合や、機能的なスタイル(優れた決定!)を使用する場合は、機能的な言語を使用してください。

0

本当にテールコールの場合、whileループやgotoでは再帰呼び出しとは大きく異なります。すべての変数をパラメータとして渡す代わりに更新するだけです。 AFAIKこれは、すべての最適化レベルでスタックの使用を制御するための、Cでの唯一のクロスプラットフォームの方法です。実際には、初期化の後にループが続く関数があるので、実際には読みやすくなります。これはかなり慣用的です。テール再帰バージョンには、初期化用と再帰用の2つの関数が必要です。

関連する問題