C ++の「翻訳単位」とは


236

私は、マイヤーズによって書かれた「Effective C ++」を読んでいて、「翻訳単位」という用語に出くわしました。

誰かが私に説明をお願いします:

1)それは正確には何ですか

2)C ++でプログラミングする場合、いつ使用することを検討すべきですか

3)C ++にのみ関連している場合、または他のプログラミング言語で使用できる場合

用語を知らなくても既に使っているかもしれません……


1
2.ヘッダーファイルが含まれている場合は、すでに翻訳単位を使用しています。これは、参照用に使用されている用語であり、c ++構成ではありません
talekeDskobeDa

回答:


268

ここから:(ウェイバックマシンリンク

標準C ++ウェイバックマシンリンク)によると、翻訳単位はC ++でのコンパイルの基本単位です。これは、単一のソースファイルの内容と、直接または間接的に含まれるヘッダーファイルの内容から、条件付き前処理ステートメントを使用して無視された行を除いたもので構成されます。

単一の翻訳単位をオブジェクトファイル、ライブラリ、または実行可能プログラムにコンパイルできます。

翻訳単位の概念は、1つの定義ルールとテンプレートのコンテキストで最もよく言及されます。


9
この用語はC / C ++でのみ使用されていますか?
dekuShrub

2
実際のところ、@ dekuShrub。たとえば、Rustでは、翻訳単位はクレートですが、C ++では同じものがライブラリ全体と呼ばれます。用語自体は普遍的であるが、それは間違いなくC.で開始
Sahsahae

この回答の内容を大まかに示す新しいリファレンス:en.wikipedia.org/wiki/Translation_unit_(programming)
ガブリエルステープルズ

67

翻訳単位は、すべてのインテントと目的のために、すべてのヘッダーファイルを含めた後のファイル(.c / .cpp)です。

http://msdn.microsoft.com/en-us/library/bxss3ska%28VS.80%29.aspx


3
ヘッダーファイルを含みます。コードが生成されない場合でも、ヘッダーファイルはコンパイラによって処理されます。JeffHのプリプロセッサコメントも参照してください。「コンパイラが認識するすべてのもの」の定義は適切です。
マルコファンデフォールト

10
「.h」で終わるファイルを問題なくコンパイルできます。ファイル名はまったく重要ではありません。内容は。「foo.h」の内容が「int main(){}」の場合は、コンパイルできます。
Johannes Schaub-litb 2009

@LightnessRacesinOrbit:ええ、私が言おうとしていたことは、インクルードを介して間接的にTUにコンパイルするのではなく、TUとしてヘッダーを直接コンパイルするのは正統ではないということでした。明らかに間違っているという最初のコメントを削除し、2番目のコメントを新しいコメントに追加しました。
GManNickG 2013

1
@GManNickG:「従来、.hファイルはコンパイラに直接提供されません。」
2013

@ JohannesSchaub-litbコンパイルではなくリンクを意味していると思います。すべての名前が定義された適切なC / C ++であれば、どのファイルでもコンパイルできます。ヘッダーファイルのポイント全体がソースファイルに含まれる(読み取りコピーされる)ため、ヘッダーファイルをコンパイルしても意味がありません。ヘッダーファイルを含むソースファイルをコンパイルすると、ヘッダーファイルは既にコンパイルされています。あなたが言うつもりだったのは、メイン関数を持たないファイルから実行可能ファイルを作成できないということです。
pooya13

30

明確に答えるのは難しい質問です。C ++標準は次のように述べています。

プログラムのテキストは、この国際標準ではソースファイルと呼ばれる単位で保持されます。すべてのヘッダー(17.4.1.2)とソースファイル(16.2)を前処理ディレクティブ#includeを介してインクルードし、条件付きインクルード(16.1)前処理ディレクティブによってスキップされたソース行を除いたソースファイルは、変換ユニットと呼ばれます。[注:C ++プログラムをすべて同時に翻訳する必要はありません。]

したがって、ほとんどの目的と目的のために、翻訳単位は単一のC ++ソースファイルと、プリプロセッサの#includeメカニズムを介してインクルードされるヘッダーまたはその他のファイルです。

他の質問について:

2)C ++でプログラミングするときにそれを使用することを検討すべき場合

あなたはそれを考慮することはできません-翻訳単位はC ++プログラムの基礎です。

3)C ++のみに関連している場合、または他のプログラミング言語で使用できる場合

他の言語にも同様の概念がありますが、セマンティクスは微妙に異なります。たとえば、他のほとんどの言語はプリプロセッサを使用しません。


1
それが明確になるかどうかはわかりません。これはややあいまいな領域になる可能性があります-たとえば、事前にコンパイルされたヘッダーが許可されていることから私が引用した標準的な段落からは明らかではありません。

1
@GMan、そしてここで、1つの定義ルールについて非常に注意する必要があります。クラスが含まれる前に、定義がわずかに異なるさまざまな翻訳単位にクラスを含めると、クラスに異なるコードが含まれ、未定義の問題が発生します。
マット価格

6
@GManは、標準で使用されている2つの用語「ヘッダー」と「ソースファイル」に注意してください。「ヘッダー」は標準ライブラリでのみ使用されます。一部のコードに含まれているユーザーファイルは、規格では「ヘッダー」と呼ばれていませんが、「ソースファイル」と呼ばれています。標準では、「。h」と「.cpp」の違いについて、私たちの貧しいc ++プログラマーが作り上げたものを認識していません:)
Johannes Schaub-litb

8

本はそれを十分に明確にします。マイヤーズが「翻訳ユニット」を指すとき、彼はソースコードファイルを意味します。


1
いいえ。彼がソースコードについて話していたなら、彼はソースファイルと言うでしょう。翻訳単位は、ソースコードをコンパイルして作られています。明確な違いに注意してください。「翻訳済み」のソースコードです。
Dan

3
@ダン:いいえ、そうではありません。翻訳単位は含まれて後にソースファイルであることができ、すなわち、コンパイル前にプリプロセッサの出力をコンパイルします。
Ed S.

1
実際、C ++標準で呼ばれているにもかかわらず、「変換ユニット」は、コンパイルされたコードの単一の「ユニット」の概念を伝えるために一般的に使用されます。実際、マイクロソフトのコンパイラの連中によれば、「翻訳単位」を直接リンクしている。 msdn.microsoft.com/en-us/library/vstudio/…–
Dan、

1
それでは、「C ++標準」のナチになることを試みているのでしょうか、それとも、業界の他の人々とのコミュニケーションを支援しようとしているのでしょうか。私はこれがC ++スレッドであることを知っているので、xcodeがtuと呼ぶものには入りません。または、用語の他のすべての定義。
Dan

1
@ダン:翻訳単位は、標準で呼ばれているものです。ランダムコンパイラの開発者の意見にはあまり関心がありません。5年近く前の投稿をnitpickに掘り下げて私の定義が間違っていると私に言った人が好転し、彼を修正するための「言語ナチ」と呼んでいるのは興味深いことです。Yeesh、次に進みます、あなたは対処するのに疲れます。
Ed S.

4

ODRに加えて、名前のない名前空間の定義では翻訳単位が重要であり、「静的」の古い使用法の1つを置き換えます。

私はまだトップの回答の下にコメントを追加するのに十分なポイントがないと思います。


3

変換単位は、適切なコンパイラに渡されるコードです。これは通常、.cファイルでプリプロセッサを実行した結果の出力を意味します。


2

CおよびC ++プログラムは、1つ以上のソースファイルで構成され、各ファイルにはプログラムのテキストの一部が含まれています。ソースファイルとそのインクルードファイル(#includeプリプロセッサディレクティブを使用してインクルードされるファイル)は、#ifなどの条件付きコンパイルディレクティブによって削除されたコードのセクションを含まず、「変換ユニット」と呼ばれます。


1

MSDNによれば、CおよびC ++プログラムは1つ以上のソースファイルで構成され、各ファイルにはプログラムのテキストの一部が含まれています。ソースファイルとそのインクルードファイル(#includeプリプロセッサディレクティブを使用してインクルードされるファイル)は、#ifなどの条件付きコンパイルディレクティブによって削除されたコードのセクションを含まず、「変換ユニット」と呼ばれます。


0

cpp / c(実装)ファイルはすべて、変換単位(つまり、オブジェクトファイル(.obj))に変換されます。cppファイルのヘッダーは、ヘッダーファイルの実際のテキストに置き換えられます。


0

他の人が言ったように、翻訳単位は基本的に前処理後のソースファイルの内容です。これは言語文法の最上位の生成物です。CまたはC ++コンパイラーを作成している場合にのみ、心配する必要があります。


1
「CまたはC ++コンパイラーを作成している場合にのみ、心配する必要があります。」私は同意しません。プログラマはコンパイラが何をしているかを理解する必要があることがよくあります。したがって、たとえば、Effective C ++の項目5の重要なポイントを理解するために、翻訳単位が何であるかを知る必要があります。「異なる翻訳単位で定義された非ローカル静的オブジェクトの初期化の相対的な順序は未定義です」。
Channing Moore

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.