中間表現

出典: フリー百科事典『ウィキペディア(Wikipedia)』
Jump to navigation Jump to search

中間表現(ちゅうかんひょうげん、: Intermediate RepresentationIR)は、コンピュータデータクロスプラットフォームで扱うために使用するデータ構造の表現である。

中間表現を用いたデータの抽象化はコンピューティング分野では一般的な手法である。異なるプラットフォームで同等の情報を保持するデータを異なるフォーマットで扱う場合に、データを中間表現で表現することで複数フォーマットへの変換処理を効率化することを手助けする。これは自然言語の翻訳に中間言語を用いるのと同等のメリットがある。

表現形態[編集]

中間表現はテキストデータバイナリデータなどのデータ構造をとる。

構文木で表すことができるデータは抽象構文木の中間表現を用いる。抽象構文木は構文木の抽象化を目的として定義され、特定プラットフォームに依存した構文木から不特定多数プラットフォームに対応できる構文木で表現される。いずれの構文木も同等の情報を保持するデータを表す。命令セットを持つデータは中間表現で抽象化した上で、特定プラットフォームの命令セットと中間表現の命令セットをシンボルテーブルで紐付ける。中間表現とシンボルテーブルをセットで定義し、各プラットフォームの命令セットを中間表現を介して変換する。

例えば、Unicodeは、プラットフォーム依存の文字コードを仲介する中間表現として策定された、如何なる文字をも含む文字コードである[1]。Unicodeエンコードスクリプトは、ASCIIEUCSJISなどのプラットフォーム固有文字コードのシンボルテーブルを持ち、Unicodeを中間表現として文字コード同士を変換して、クロスプラットフォームで文字データを扱うことを手助けする。

中間言語[編集]

中間言語: Intermediate Language)は、プログラミング言語プログラムの間に存在する言語の形態をとった中間表現である。中間言語はプログラミング言語と同様に言語仕様で定義され、コンピュータが解釈する機械語に比べて、人間が比較的解釈しやすい言語である。プログラミング言語アセンブリ言語バイトコードなどの種類がある。

各種ソースコードと各種マシンコードを中間言語で中継するコンパイルのシーケンス

中間言語はコンパイラソースコードからマシンコードを生成する際の中間表現として利用される。コンパイラは、コンパイラのフロントエンドが異なるプログラミング言語のソースコードを1つの中間言語に変換し、コンパイラのバックエンドが1つの中間言語を異なるプラットフォームのマシンコードへ変換する[2]。コンパイラが中間言語を介してコンパイルすることで、プログラミング言語はクロスプラットフォームのパラダイム特性を持つことができる。n種類のプログラミング言語からm種類のプラットフォームへコンパイルする場合、中間言語を用いなければ種類のコンパイラが必要となるが、中間言語を用いれば種類のコンパイラのみを必要とする。中間言語からマシンコードへ変換するコンパイラのバックエンドはコンパイラ基盤と呼ばる。例えばLLVMclangrustcEmscriptenなどのコンパイラ基盤として使われている。コンパイラが扱う中間言語の概念は、1958年にメルヴィン・コンウェイProposal for an UNCOLで提唱し[3]、同論文で中間言語としてUNCOL英語版が紹介されている。UNCOLは中間言語の概念を提案する目的で定義された中間言語であり、完全な言語仕様は策定されていない。

中間言語は、中間言語として設計されたUNCOLやC--の他に、プログラミング言語として設計されたが中間言語としても利用されるC言語なども存在する。他言語コードからC言語コードにトランスパイルして、C言語コードからマシンコードにコンパイルすることがある。この場合、C言語は他言語コードとマシンコードを繋ぐ中間言語となる。

初期のBASIC処理系の実装で用いられた中間言語は、バイトコードのようなものではなく、字句解析のみを行い、BASICの各ステートメント(ないしコマンド)を単にコードに直接変換するだけといったものもあった。実行時の字句解析が不要になるが、ソースコードに戻して表示、編集することもできる。GOTOの飛び先をキャッシュするなどの工夫がされたものもあった。高度な中間言語を利用する実装もあり、N88-日本語BASIC(86)(MS-DOS版)のコンパイラは、実行ファイルを出力するが、その内部は中間言語コードでありまたその実行には外部に、中間言語のインタプリタを含むランタイムライブラリが必要だった。

幾つかのバーチャルマシンインタプリタなどのランタイム(実行環境)は中間言語を直接実行する。ランタイムはプラットフォーム毎の中間言語とマシンコードの命令セットをマッピングしたシンボルテーブルを保持し、シンボルテーブルに従ってリアルタイムに中間言語をマシンコードへ変換してプログラムを実行する。

プログラミング言語
中間言語であるプログラミング言語は基礎的な機能のみが定義されたプログラミング言語である。機械語の命令セットがカバーする範囲に近しい範囲の命令セットのみをサポートし、高級プログラミング言語ほどの文法・機能の柔軟性を持たない。C--は中間言語として設計されたプログラミング言語である。C言語に似た文法を持つが、C言語より小さい言語仕様で定義されている。
アセンブリ言語
アセンブリ言語は機械語を人間にとって可読性のある表現に置き換えたプログラミング言語である。アセンブリ言語と機械語の命令セットシンボルテーブルで対に定義することができる。シンボルテーブルを複数用意することが出来るならば、アセンブリ言語は特定プラットフォームに依存しない中間言語となりえる。GNUアセンブラ(GAS)・LLVMアセンブリ(LLVM IR)・MS CILはクロスプラットフォームの中間言語である。
バイトコード
バイトコードはバイト指向の中間表現である。人間が直接解釈するのは些か難しいが、バイト単位で命令セットが定義されている。アセンブリ言語より更に機械語に近い表現形態である。幾つかのバーチャルマシンインタプリタなどのランタイム(実行環境)はバイトコードを解釈してプログラムをクロスプラットフォームで実行する。

データ記述言語[編集]

データ記述言語は、異なるデータ表現の間に存在する言語の形態をとったデータ構造の中間表現である。データ記述言語は言語仕様で定義され、テキストで表される。プラットフォーム依存のデータ表現Aとデータ表現Bを仲介する目的で定義・利用される。例えば平文テキストと装飾テキストの中間表現としてHTMLLatexがある。他に任意の文字データを保有するCSVJSONXMLがある。

データ記述言語は中間言語に比べて中間表現のまま人の目に触れることが多い。中間言語はコンパイラという1つのソフトウェアの中で完結するが、データ記述言語はテキストエディタとテキストパーサーなどの複数のソフトウェアで扱うためそれぞれのソフトウェアを利用する人間が目視する機会が増える。XMLのようなデータ記述言語は人間が目視してデータ内容を解釈できるよう、人間による解釈を手助けするためにタグに自然言語の単語を用いることがある。XMLはCSVやJSONに比べて人間が解釈しやすいデータ記述言語であり、人間が解釈する機会が多いデータの中間表現ではCSVやJSONよりXMLが好まれる場合がある[4]。一方で、XMLはCSVやJSONに比べて記述量が多く人間が直接管理する必要がない場合には冗長なデータ記述言語であり、人間が解釈する必要性が少ないデータの中間表現ではXMLよりCSVやJSONが好まれる場合がある[5]

脚注[編集]

  1. ^ What is Unicode?”. Unicode Consortium. 2018年4月25日閲覧。 “The Unicode Standard provides a unique number for every character, no matter what platform, device, application or language. It has been adopted by all modern software providers and now allows data to be transported through many different platforms, devices and applications without corruption.”
  2. ^ David Chisnall (2017年6月12日). “Modern Intermediate Representations (IR) (pdf)”. University of Cambridge. 2018年4月22日閲覧。
  3. ^ Melvin E. Conway. “Proposal for an UNCOL”. Communications of the ACM. 2018年4月22日閲覧。
  4. ^ The World Wide Web Consortium Issues XML 1.0 as a W3C Recommendation”. W3C (1998年2月10日). 2018年4月27日閲覧。
  5. ^ JSONに押されるXMLの存在”. Publickey (2010年12月10日). 2018年4月27日閲覧。