Comefrom文

プログラミング言語におけるcomefrom文とは、コード内の任意のポイントから、そのcomefrom文の場所へ制御がジャンプするという制御構造のひとつである「文」である。goto文とほぼ反対の働きをするものであり、元々は冗談として提唱されたものだったが、一部のプログラミング言語で実際に実装されている。gotoがgo toとも書かれるように、comefromもcome fromとも書かれる。

1. 概要
-----

コード内の移動元のポイントは、通常comefromの引数として指定される。指定されたポイントで移動が発生するかどうかは、使用される言語によって異なる。同じ移動元を指定するcomefrom文が複数ある場合、言語によって、そのようなcomefromは無効となるもの、非決定的となるもの、定義済みの優先順位で実行されるものや、INTERCALのような並列計算もしくは並行計算が行われるものがある。

comefrom文の簡単な例"comefrom x"で説明する。この文は、トラップドアとして機能するラベル x と対になって使用される。このラベルは、対応するcomefrom文の近くに物理的に配置する必要はない。コードの実行がラベルに達すると、対応するcomefrom文に制御が移動する。if文の中にラベルがある場合は、goto文の場合と同様に、if文の条件が満たされた場合のみ移動が行われる。goto文がコードのローカル構造のみに依存するのに対し、comefrom文はグローバル構造に依存する。goto文の場合はgoto文のある行に到達すると無条件に制御が移動するが、comefrom文は、ラベルのあるスコープ内にcomefrom文があるか確認し、条件がヒットしたかどうかを確認するために、プログラムまたはスコープ全体をスキャンする必要がある。これにより、デバッグが非常に困難になる。これは、問題の行やラベルの近くに制御のジャンプ先を示すものがなく、その行またはラベルを参照しているcomefrom文をプログラム全体から探す必要があるためである。

Python gotoモジュールでは、デバッガフックを使用してcomefrom文を実装できる。また、Linuxカーネルの構成オプション CONFIG_JUMP_LABEL で使用されるgcc機能"asm goto"でも実装できる。 no-opの場所は保存されており、no-opの後に命令に戻る実行可能フラグメントへのジャンプに置き換えられる。

2. 歴史
-----

comefromは、冗談のアセンブリ言語の命令'CMFRM'として現れたのが最初である。これは、1973年に『データメーション』誌に掲載された、R・ローレンス・クラークによるエドガー・ダイクストラの文書「Go To Statement Considered Harmful」に反応した記事にて詳しく説明されていたものである 。

comefrom文は最終的に、難解プログラミング言語の1つであるINTERCALの変種であるC-INTERCALに、さらに曖昧な'computed comefrom'とともに実装された。また、Fortranに、既存のdo文を補完するための'assigned COME FROM'と'DONT'を追加する提案もあった。

2004年4月1日、Richie Hindleが、Python用のGOTOとCOMEFROMの実装を公開した。エイプリルフールに公開されたものであり、真面目に使用することを意図したものではないが、構文は正当であり、実装は完全に機能する。

3. 実用的な用途
---------

3.1. BASIC
----------

以下は、"GOTO"の代わりに"COMEFROM"を使用した架空のBASIC方言のプログラムの例である。

10 COMEFROM 40 20 INPUT "WHAT IS YOUR NAME? "; A$ 30 PRINT "HELLO, "; A$ 40 REM

このプログラムは、ユーザに名前を質問し、入力された名前に対し挨拶をするという動作を繰り返す。行40の命令"REM"は、単なるNOPである。行10の"COMEFROM"文は、その内容に関係なく、実行が行40に達するとこの行に戻る。

3.2. Python
-----------

以下に、joke gotoモジュールがインストールされたPythonでの完全に実行可能な例を示す。

from goto import comefrom, label

comefrom .repeat name = raw_input if name: print label .repeat print<WtXmlEndTag />

3.3. Ruby
---------

以下に、Intercal comefrom文のRubyでの実装を示す。 $come_from_labels = {}

def label if $come_from_labels[l] $come_from_labels[l].call end end

def come_from callcc do |block| $come_from_labels[l] = block end end<WtXmlEndTag />

3.4. OS/360 Fortran G
---------------------

OS/360のFortran Gコンパイラには、デバッグパケット機能がある。その"AT"文は、制御フローをデバッグブロックに渡すという点でcomefrom文に似ている。ブレークポイントは一般的に似ている。

例1：SOLON、GFAR、EWELLの値は、文10の完了時に検査される。AT文は文11を示す。 INTEGER SOLON, GFAR, EWELL . . . 10 SOLON = GFAR * SQRT) 11 IF  40, 50, 60 . . . DEBUG UNIT AT 11 DISPLAY GFAR, SOLON, EWELL END

例2：文35が検出されると、STOCKの全ての値が表示される。 DIMENSION STOCK,OUT . . . DO 30 I=1, 1000 25 STOCK=STOCK - OUT 30 CONTINUE 35 A = B + C . . . DEBUG UNIT AT 35 DISPLAY STOCK END

例3：トレースは文10で始まり、ループの実行中に文20でトレースが停止し、ループの後に再開する。文30が実行される直前にトレースが停止する。 10 A = 1.5 12 L = 1 15 B = A + 1.5 20 DO 22 I = 1,5 . . . 22 CONTINUE 25 C = B + 3.16 30 D = C/2 STOP . . . DEBUG UNIT, TRACE C DEBUG PACKET NUMBER 1 AT 10 TRACE ON C DEBUG PACKET NUMBER 2 AT 20 TRACE OFF DO 35 I = 1,3 . . . 35 CONTINUE TRACE ON C DEBUG PACKET NUMBER 3 AT 30 TRACE OFF END

4. 関連項目
-------

マイケル・W・シールズ  - comefrom文の意味論の専門家
INTERCALcomefrom文に類似した概念

アスペクト指向プログラミングにおける
継続
MATLAB SimulinkにおけるGoto/From signal routing block

5. 脚注
-----

6. 外部リンク
--------

[1]
[2]
[3]
[4]