ここ最近AppleのSwiftを触っていて感じた個人的な感想だが、Swiftは今のところ「静的型付け言語界のJavaScript」に最も近い位置にいると思う。
JavaScriptは、第一級関数やクロージャがお仕事でよく使われるメジャーな言語に既定で組み込まれたという点で、ある意味画期的な言語だ。第一級関数やクロージャが組み込まれた言語自体は遥か昔からあったものの、猫も杓子も使っている言語にまで降りてきて、しかも少なくない人たちがそれらの機能を使うようになったという点で、JavaScriptの影響は大きい。*1
Swiftの場合は、コンパイラによる強力な型推論と型安全性のチェックだろうか。これらの機能を持つ言語も、やはり以前より存在した。比較的最近のメジャーどころでも、OCaml・Haskell・Rustなどがぱっと思いつく。思いつくのだけど、Apple帝国公用言語という良くも悪くもそこそこ多くのサードパーティ開発者が使用するメジャーどころに降りてきたという点で、Swiftのインパクトは大きいと思う。*2
……というかObjective-Cの新規情報量が激減しすぎだ。iOSアプリ開発の入門書なんてSwift版ばかりで、Objective-Cベースの本が消えてしまった。つい先日のことだけど、リアル書店に『詳解 Objective-C 2.0 第3版』や『Effective Objective-C 2.0』が無くてAmazonに頼ることになった。うーん、実際のユーザ数的には、さすがにまだObjective-Cの需要はあると思うんだけどなあ。
(あ、記録のために書いておくと、単純な言語デザインの良し悪しではSwiftの方が遥かに上だ。JavaScriptは、個人的には割と好きだけど、でも言語デザインに色々と問題を抱えているのは事実だからなあ)
Swift雑感
SwiftはObjective-CやObjective-C++とは異なり、CやC++の拡張ではない、完全に新規開発された言語だ。
おそらく、言語自体の後方互換性を捨てたからこそ、型システムまわりを刷新できたのだろう。例えば、C++11では型推論が組み込まれたものの、後方互換性の影響か、ほんの少しだけ中途半端な感じになっている印象を受ける*3。
とはいえ、過去の資産(Objective-Cと、Foundationなどの既存のフレームワーク)からは逃れられなかったようだ。
例えば、関数の引数に仮引数の名前とは別に「引数名」を付けることができる点などは、完全にObjective-Cの流儀そのままだ。また、Any型の存在は、NSArrayなどのコレクションがid型のオブジェクトを格納するようになっているために、1つのコレクション・オブジェクトの中に複数種類のクラスのオブジェクトを格納できる点を考慮してのものだろう。
そのような配慮があるからこそ、Objective-Cで書かれたコードをSwiftから利用したり、逆にSwiftで書かれたコードをObjective-Cから利用したりする際に、違和感が少なく済むようになっている。
この辺は、Foundationなどの既存のフレームワークを最小限のコストで流用可能とするための仕掛けでもあったのではないかと妄想している。Appleの開発者は、フレームワークを再実装する必要がない。サードパーティの開発者は、構文こそ違えども、今まで使い慣れたフレームワークを利用できる。双方にメリットがある訳だ。
まあ、Swiftの仕様にてObjective-Cに配慮するだけでは足りなくて、Objective-C側もinstancetype・ライトウェイトジェネリクス・null許容性アノテーションなどの誠意を求められるのだけど、それだけで済むというのも興味深い話である。
鬼が笑う話
Swiftは今以上に広まるだろうか? 少なくともAppleはSwift推しだ。iOSもmacOSも、新規に書かれるコードでSwiftが採用されることを望んでいるだろう。
Linuxなどの他のプラットフォームに広がるかどうかは、正直ちょっと微妙だろう。といかライブラリが足りない。Swiftの標準ライブラリは小さい。Foundationなどの既存のフレームワークを使う前提になっている。だが、これらのフレームワークはAppleのプラットフォームでしか動かない。
(代替となりそうなGNUStepは、資金も開発者も不足しているからなあ……)
ライブラリの薄さの問題が解決されないと、他のプラットフォームへの布教は望めないように思う。せめてFoundationフレームワークぐらいはLinuxでも簡単に使えないと。「import Glibc」だけではiOS・macOSとそれ以外とで分断が起きてしまい、Objective-CのようにApple専用言語になりかねない。
Swiftが広まると仮定するとして、Objective-Cはどうなるだろうか? 案外、グルー言語として生き残るのではないかと思う。
プラットフォームへの囲い込み競争が激化している昨今だが、サードパーティの開発者としては、どうしてもクロスプラットフォーム開発にシフトせざるを得ない。
クロスプラットフォーム向けのフレームワークは色々とあるものの、デスクトップとスマホ・タブレットに加えてIoT機器までとなると、既存のフレームワークでは厳しくなってくる。そうなると、コスト増を承知した上で、コア部分を自前でクロスプラットフォーム化する必要が生じる。
例えばコア部分をCやC++で実装しておけば:
- Windowsアプリでは、MFCに組み込むか、DLL化してC#などから利用する。
- iOSやmacOSでは、Objective-CやObjective-C++から利用する。
- AndroidではNDK経由で利用する。
- IoT機器では、CやC++にそのまま組み込む。あとはQtなどのC++前提のフレームワークを使うとか。
――みたいな感じで使える。もちろん各プラットフォーム専用のフレームワークを使う必要はなく、例えばデスクトップ向けとスマホ・タブレットとで別々のクロスプラットフォーム向けフレームワークを使うなど、工夫の余地はあるだろう。
要は、そのアプリ固有のノウハウ部分の実装を共通化したい訳だ。で、昨今のクロスプラットフォーム向けフレームワーク登場よりも前に、コストをかけてCやC++でライブラリ化されたものは意外と多い。
で、だ。今まではObjective-CやObjective-C++に直接組み込めばよかったが、Swiftでは不可能だ。Cならともかく、C++の場合はObjective-Cでラッピングすることになる。
今しばらくは、Objective-CはC++のコードをラッピングするためのグルー言語として使われるのではないかと思う。ヘッダファイルはObjective-Cで、ソースファイルはObjective-C++で、C++11やC++14などの機能を織り交ぜつつ書き、そしてアプリ本体はSwiftで実装する。1つのアプリで3言語だなんて、プログラマは大変だ。
追記:2017-05-21
これを書いた数日後にGoogle I/OでKotlin正式サポートがアナウンスされるとは……。
「静的型付け言語界のJavaScript」になるのはSwiftかKotlinか、ちょっと分からなくなってきた。