Goto文

プログラミング言語におけるgoto文（ゴートゥぶん、英: goto statement）とは、手続き列中の指定された場所（専らラベルで指定される）に無条件にジャンプ（移動）する、という制御構造のひとつである「文 (プログラミング) 」である。古い文献などで "go to" と離していることもあるのは、英語の go to どこそこ、といったような言い回しとの類似のためでもあり、FORTRANではプログラム中の空白は基本的に無視されるので、goto でも go to でも同じだったからという理由もある（BASICにも、どちらも使えるようにしているものもある）。

概要

goto文は、それ単体では働きを持たせることはできず、必ずラベルか何かによって飛び先が必要である。飛び先のほうにcome fromという文を置き、飛ぶ元にラベルを置く、という「come from文」という（冗談半分ではあるが）提案もある（en:COMEFROM。提案自体はジョークだが、同等の機能がある言語は実際にいくつかあり、プログラムの理論上の研究対象にもなっている）。機械語における分岐命令の一種である無条件分岐と、アセンブリ言語のラベルをそのまま手続き型プログラミングに持ち込んだものと言え、何らかの条件分岐との組み合わせによって、ループであるとか、コードブロックの飛び越しであるとかいったような機能の一部となることができる。
「以前に実行した場所に戻る」というループ用途なのか、それともこの先にあるコードは別の流れの一部なので「単に飛び越したいだけ」というジャンプ用途なのか、という単純なことすら、goto文ではその見かけからは分からない。if文やwhile文と比較して考えれば、そういった「意図の不明瞭さ」は明白であり、後述のように、if文やwhile文で単純に書けることであれば、gotoは使うべきではない。一方で、深く多重にネストしたループからの脱出など（そもそも、そのようなループ自体に問題があることもあるとは言え）、gotoを使ったほうが単純かつ明確に書ける場合もあり、特にC言語においてはgotoを教条的・無条件に排除するべきではない。
資源の確保と解放などのために、プログラム片の入口と出口が必ず対応している必要がある、といった場合などは、gotoに限らず、いわゆる「途中return」等の他の多くの技法も制限されるので、以下のgoto文の議論とはきちんと区別すべきであるし、またそういった場合の制限を全てのコーディングに適用するべきではない。

構文

次のように、ラベルの付いた文と併用する。
clear:
    x = 0;……goto clear;
goto文によって、そこからclearラベルの付いた文にジャンプし、そこから処理を続ける。

批判

Cなどの構造化プログラミング言語においては、goto文はむやみに使ってはいけないというルールが、プロジェクト等のガイドライン等として定められていることがある。これは、goto文が原始的で自由度の高すぎる機能であるため、安易なgoto文の使用はプログラムの構造化を妨げ、デバッグなどが行いにくくなり、バグの発生や、メンテナンス性・可読性の低下の原因になりやすいからである。
しかし、多重にネストしたfor文やif文、while文などでエラー処理や例外処理などが複雑になる場合はgoto文を使った方がプログラムがすっきりと書けるケースもあるため、プログラムの構造を熟知したプログラマが状況に応じて使い分けるものとされている。
エラー処理や例外処理、RAIIなどの仕組みが充実している言語の場合、goto文が必要になるケースが少ない。この傾向はC言語よりも後発のオブジェクト指向言語で顕著である。そのため、言語仕様として始めから用意されていないケースもある。こうした言語としては、Javaなどが挙げられる。一方では、PHPで、2009年にリリースされたバージョン5.3からgotoが追加されたように、高度化する言語構造の中でgoto文が一定の再評価を受ける例もある。
BASICの様な言語や低レベルの制御言語ではgoto文は不可欠であり、goto文を利用しないと分岐やループを使ったプログラムが記述出来ないものもある。しかし、拡張されたBASICの中には、goto文がほとんど不必要になってしまっているものもある。
前述のように、goto文の安易な使用はプログラムの可読性を著しく低下させる。こうした可読性の低いコードのことを、制御構造が複雑に絡まっているという意味を込めて、スパゲティコードと呼ぶことがある。

goto文論争

「構造化プログラミング」を提唱していたコンピュータ科学者らの一人であったダイクストラは、1968年にGo To Statement Considered Harmful（「Go To 文は有害（Harmful）とみなされる」）という刺激的な記事を国際学会ACMの学会誌Communications of the ACMに投稿し（ただし、本人が付けたタイトルはA Case Against the Goto Statementという穏便なもので、少なくともタイトルの過激さと、レターとして発表を急いだことは、編集を担当していたヴィルトによるものである）、こんにちでは構造化プログラミングに関して最も良くその名前だけが知られている論争となっている（その内実は言葉の有名さの割には全く知られていないし、そもそも内容や意味の理解は半世紀という時代の違いによって、かなり難しくなっていることも確かである）。クヌースの言葉を借りるならば、「go to 文除去の話の二番目の場面は，多くの人たちが第一幕だと思っている事実である．」（という解説自体も1974年に書かれたものである）。
また considered harmful というフレーズはその後、定番ネタとして、しばしば似たような深刻な、あるいは軽妙な論争に関して付けられるものとなっている（英語版en:Considered harmfulの記事などを参照）。

goto擁護派

一方、goto文を使わずに3つの基本構造による代替を行うと、理論上は同値であっても実際にはプログラムの実行速度や記憶容量の点で性能が劣化する場合があることを示し、goto文を擁護する意見もあった。
前の節で述べたように、本来の主張では、goto文は全て3つの基本構造による代替によって書けるのだから、それにより書き換えよう、などという主張ではなかったので、「理論上は同値であっても実際にはプログラムの実行速度や記憶容量の点で性能が劣化する場合があることを示し、goto文を擁護する意見」というものが、そもそも変である。
ACMの年次大会(1972)の討論会では、トップダウンでプログラムを分割するよりgoto文を使う方が適した事例があり、証明には関心がないという意見(William Wait)や、goto文を残せば選択の余地があるが、無くしてしまうと必要になったとき困るだろうという意見(Guy Steel)などが出された。
条件文とgoto文を正しく使うことで、FORTRANでもALGOLの基本機能を実現できることを例に挙げ、プログラマは必要な機能がプログラミング言語で直接表現できないとき、どのように実装するか工夫できるべきであるという主張もあった(S.W.スリア)。
また、ドナルド・クヌースは「go to 文を用いた構造的プログラミング」（『文芸的プログラミング』収録）の中で、いくつかのgotoを使ったほうが良いだろうという例を挙げているが、その中には、再帰呼出しのある正当なプログラムを、正当な変形によってループによるプログラムに書き換えた結果「ループの中に飛び込むgoto」になる、といったような例も挙げている。

gotoの現在

現在C言語を除く主流派の言語では、そのままのgoto文はほとんど見られなくなった。替わりにbreak文、continue文、もしくは例外処理のような特殊脱出(去勢されたgotoとも呼ばれる（実際には関数呼出しをまたいだ、いわゆる大域脱出もできるのだから、gotoよりも例外処理のほうが強力である（が、それを理解できない者も多い））)をサポートし、単純な制御構造だけでは弱いと考えられる部分を補っている。さらにクロージャやコードブロック、継続のような強力な制御機構を使い、抽象度の低いgoto文を使う必要性を低くした言語もある。例えばHaskellにおいてはモナドを利用して例外や非決定性計算などの様々な制御構造を表現できる。またSmalltalkやIoにおいても制御構造はブロックを扱うメソッドとして表現している。Scheme等でサポートされている継続は「引数付きgoto」と呼ばれることもある。
一方で、例えば1999年から設計されたD言語はgoto文を含んでいる。PHPにも2009年にリリースされた5.3において制限された形ではあるがgoto文が追加された。

その他の話題

それまでの職人芸的なプログラミングの時代から、構造化プログラミングというパラダイムの提唱によって、プログラミング技法の体系化を試みるプログラミング工学という学問が芽生えたと言っても過言では無いだろう。
なお、論文“Go To Statement Considered Harmful”は、その半ば挑戦的な題名がプログラミング以外の様々な分野に及んで評判となり、それをもじった様々な “～ Considered Harmful”といった論説やジョークが生まれたen:Considered harmful 。極めつきは、何かが有害であることだけが強調される題名の有害性を指摘した“‘Considered Harmful’ Essays Considered Harmful”であろう。同じくWhat led to "Notes on Structured Programming" においてダイクストラは、Millsによって矮小化されたgoto文廃止という概念のもと、IBMが用語としての「構造化プログラミング」を盗用したと語っている。
ダイクストラの著書は、分かりにくいことと誤解を招きやすいことで定評がある。それを憂いたディビット・グリースは、ダイクストラ流のプログラミングについて体系化した書籍「プログラミングの科学」(The Science of Programming)を書いた。

gotoを使用しなかったことによる大規模障害

1990年1月15日に起きた、AT&Tの長距離電話網の停止 (crash) は、break文による脱出先の勘違いによるものであった。en:List of software bugs#Telecommunicationsも参照。
そもそもソフトウェアの制御パステストを十分に実施していなかったせいで不具合が発見されなかったことが障害につながったのだが、適切な名前のラベルを用意し、ループ脱出にgotoを使っていれば避けられたバグでもあった。