USトップ大学でも関数型プログラミングが余り教えられていない現実

数カ月前、私たちは一部の言語が他の言語に比べて受け入れられやすい理由を調べたSocioPLTリサーチプログラムについて投稿しました。その調査の一環として、2000年から2010年の期間内にSourceForgeのプロジェクトで使用された言語を調べて頻度別にランク分けしたのですが、この結果で興味深かったのは、上位20の言語の中に関数型言語が1つもなかったということです。

教育機関のプログラミング言語研究者は関数型言語を好む傾向にあるため、この事実を残念なことと思うでしょう。しかしながら、このような事態に陥った原因の一部は、私たち学術研究者自身にあるのかもしれません。関数型言語が“現実の世界”で受け入れられるためには、大学などの機関がそれを教えなければならないからです。この投稿を通じて、そうした教育プログラムを持つ大学がほとんどないことが分かるでしょう。プログラミングの教育課程において関数型プログラミングが重要な位置を占めているのは、アメリカの大学上位33校のうち9校のみで、それら33校のうちの4割では関連の授業さえ行われていません。

なぜ関数型言語なのか?

プログラミング言語の研究者たちが関数型言語を好むのには、十分な理由があります。例えばC言語のような命令型言語の場合、プロシージャのコード1行がプログラム全体に影響を与えてしまうこともありますが、関数型言語の場合はそういった副作用が大幅に制限されるため、正確性や安全性を導くのが容易になります。どういうことかと言うと、AのプロシージャとBのプロシージャの構成の正確性を分析する際には、AとBを分けて個別に分析できる利点があるということです。また研究者たちは、関数型プログラミングによる設計が並列処理の活用を容易にするということも度々論じています

なぜ関数型プログラミングは人気がないのか?

それでは、なぜ関数型言語は“現実の世界”で人気がないのでしょうか? その理由を考える前に、まずは余談から入りたいと思います。

“関数型プログラミングは非効率的”といった議論は、今ではほとんど(仮に過去にあったとしても)意味があるとは思えません。その第一の理由として、コンパイラ技術が進歩したことで、関数型言語の実装が過去にないほど簡単になっていることが挙げられます。一例として、C++と関数型言語のOCamlで書いたレイトレーサのサンプルデータを比較してみましょう。実装のパフォーマンスは同等ながら、Ocamlのプログラミングの方がC++のバージョンに比べて、行数が約半分(47%)で済むことが見て取れるかと思います。続いて第二の理由として挙げられるのが、SocioPLTの研究者が行ったプログラマへの調査の結果です。それによると、プログラマがプロジェクトの言語を選択する際、言語のパフォーマンスで選ぶという回答は上位5番目にも達しなかったといいます。

同じ調査では、言語の使用や好みに関わる最も重要な要因はライブラリが使用できるかどうかだということも示されました。このことは、例えばPythonの人気を裏付けるものでしょう。しかし、この要因が、関数型言語が不人気であることの主な理由であるというのは、いささか信じ難いものがあります。もしそうであれば、関数型プログラマが全ての.NETインフラストラクチャを使うことができるようなF#言語などは、今頃主流になってもいいはずですが、そのような兆候は今のところ見受けられません。

本当の問題: 教育

関数型プログラミングにおいて、極めて最大の問題だと私が考えるのは、ほとんどのプログラマがこのプログラミングのスタイルに慣れていないという点です。このことはSocioPLTの別の調査により裏付けされており、調査対象の22%の人しか関数型言語になじみがないという結果が出ています。学校で関数型言語を“学習済み”であるとした人の中では40%でした(高くなってはいるものの目覚ましい数値ではありません)。対照的に、少なくとも94%の人がC/C++、Java、C#のいずれかを知っており、また少なくとも79%がPerl、Python、Rubyのいずれかを知っていました。

このことから、大学のコンピュータサイエンス系の学部では学生に対して関数型プログラミングに接する機会をうまく与えられていないと考えずにはいられません。関数型プログラミングを教えている場合でさえ、次第に薄れていってしまうほど表面的に扱っているだけです。

あなたが特に関数型言語のファンではなくても、このことは問題と見なすべきです。関数型言語でプログラミングすることで、学生は、データが帰納的に定義出来ることや、たくさんの興味深いアプリケーションが基本的にデータ型のパターンマッチを使っていることや、コードは本質的にデータとは異なることや、副作用を最小限に抑えることで連結が楽になることなど、重要な見識を広げます。これらは例えあなたがJavaやC++でプログラミングするつもりであったとしても有用な見識なのです。

誰が関数型プログラミングを教えるか?

以上のことを踏まえると、恐らく、関数型プログラミングを教える学校とそうでない学校を調査する価値はあるでしょう。Philip Guoが最近、CACM blogで、アメリカの大学の上位39校(US News rankingsで取り上げられた)で使用される初心者向けの言語に関する記事を投稿しました。それらの大学のうち5校のみが、CS0またはCS1のコースで関数型言語であるSchemeを使用しており、MLまたはHaskellといった静的型付き関数型言語を使用しているのは“0または1”校のみでした。いくつかの大学ではSchemeからPythonへ使用言語を変更しています。このデータから、大学1年目で関数型プログラミングを学習する学生はほとんどいないということは明らかです。

では、いくつの大学で、学生に関数型言語を何らかのレベルで真剣に教えているのでしょうか。これに関するデータはどこにも見つからなかったので、掘り下げてみることにしました。以下はUS News 2014で上位30校にランキングされたアメリカの大学と、そこで最初に提供される本格的な関数型プログラミングのコースについて表にまとめたものです。集計に使われたコースは以下の条件を満たしています。

  • コースは相当量の関数型プログラミングを扱っているものとします。“課題の30%以上が関数型プログラミングを含んでいる”と定義しました。
  • コースは定期的に開講されており、2013年または2014年に提供されている必要があります。
  • 講義は一般的な内容である必要があります。例えば、イェール大学はコンピュータを使用した音楽の講義があり、そこで学生は(見たところ)Haskellで相当量のプログラミングを行っています。これを私は集計には含めていません。一方で、関数型言語を使ってコンパイラやプログラミング言語の実装を行う講義は集計に含めています。

必修、または大多数の学生が受講する講義は太字で示しています。

学校 コース 言語 講義の種類
カーネギーメロン大学 15-150 ML プログラミング
マサチューセッツ工科大学
スタンフォード大学 CS 240h Haskell プログラミング
カリフォルニア大学バークレー校
イリノイ大学アーバナ・シャンペーン校 CS 421 OCaml プログラミング言語とコンパイラ
コーネル大学 CS 3110 OCaml プログラミング
ワシントン大学 CSE 341 SML, Racket プログラミング言語
プリンストン大学 COS 326 OCaml プログラミング
ジョージア工科大学
テキサス大学オースティン校
カリフォルニア工科大学 CS 4 Scheme プログラミング
ウィスコンシン大学
カリフォルニア大学ロサンゼルス校 CS 131 OCaml, Scheme プログラミング言語
ミシガン大学
コロンビア大学 COMS W4115 OCaml プログラミング言語とコンパイラ
カリフォルニア大学サンディエゴ校 CSE 130 OCaml, Scala プログラミング言語
メリーランド大学 CMSC 330 OCaml プログラミング
ハーバード大学 CS 51 OCaml プログラミング
ペンシルベニア大学 CIS 120 OCaml プログラミング
ブラウン大学 CSCI 0170 Scheme, ML プログラミング
パデュー大学 CS 456 Haskell, ML プログラミング言語
ライス大学
南カリフォルニア大学
イェール大学 CS 421 ML プログラミング言語とコンパイラ
デューク大学
マサチューセッツ大学 CMPSCI 220 Scala プログラミング
ノースカロライナ大学チャペルヒル校
ジョンズ・ホプキンス大学
ニューヨーク大学
ペンシルベニア州立大学
カリフォルニア大学アーバイン校
ミネソタ大学 CSCI 2041 ML プログラミング
バージニア大学 CS 4610 OCaml プログラミング言語

結論

表を見てみると、ある学校では関数型プログラミングをプログラミング教育課程で教えていることが分かります。その中のいくつかの学校(例えばミネソタ大学)にとっては最近の取り組みと思われます。もちろん、ここ数年で関数型プログラミングをコア・カリキュラムから外した学校(いくつか名前を挙げるとマサチューセッツ工科大学やカリフォルニア大学バークレー校そして我がライス大学)もあります。関数型プログラミングをプログラミング教育課程で教えている学校の数は近年増えているのか減っているのかは定かではありません。

ある学校では、関数型プログラミングをプログラミング言語の講義で教えています。これは最適とは言えません。なぜなら、ほとんどの場合でこれらのコースは必修科目ではないだろうからです。また、関数型プログラミングをインタプリタやコンパイラの設計をする特定のアプリケーションと関連づけて教え過ぎてしまいます。もちろん、これは関数型プログラミングを全く教えないよりはまだましです。不運にも、マサチューセッツ工科大学やミシガン大学といった有名大学を含む多くの学校が学生に関数型プログラミングと接する機会を与えていないのです。

どうすれば変えられるのか? もちろん、大学のカリキュラムはゼロサム・ゲームです。多くの大学で、新しくプログラミングの必修講義を設けるための枠がないのです。可能性の1つとして、低いレベルの必修コースに関数型プログラミングを取り入れる方法があります。私の見解では、データ構造やアルゴリズム入門のコースは関数型プログラミングを広める素晴らしい手段になると思います。いくつかの学校では既にこういったコースを設けています。例えば、カーネギーメロン大学のデータ構造とアルゴリズムのコース(15-210)では最近、特に永続データ構造や並列処理の活用に重点を置いて、関数型プログラミングのみを扱うように改変しました。コーネル大学のCS 3110ではまた別の形で優れたコースを設けています。

また、“何か”に関連付けた関数型プログラミングを教える講義がより多くなると良いでしょう。“何か”とはインタプリタやコンパイラ、そしてプログラミング言語の基礎以外の別のものです。私の調査では、そういった講義はあまり見つけられませんでした。例外のコースとしてはパデュー大学のCS 390があります。このコースは並列処理と並行処理を学ぶものですが、その約30%で関数型プログラミングを用いています。他のコースとしてはスタンフォード大学のCS 240hがあります。このコースではHaskellを用いたシステムソフトウェアの作成を教えています。しかし、明らかにもっと多くのコースで同じようなことが出来るはずです。例を挙げるなら、私が見たいのはF#言語を使用したデータサイエンス、またはHaskellを使用した安全なシステム構築です!

[注意:私が集めたデータが正しいかどうかは保証できません。もし間違った点があれば、コメントでご指摘ください。適宜修正致します。]