僕がJavaを選ばなかった理由

先日、大学時代の後輩と久しぶりに会った。彼はSeasarのコミッタにもなっているとても優秀なJavaプログラマだ。

その彼が、ビールを片手にこう尋ねた。

「どうしてC#にしたんですか?Javaを選ばなかった理由って何かあるんですか?」

僕は答えた。

Javaにはstructがないから、かな。」

彼はずいぶん驚いた様子だった。

「えーっ?struct?・・・そんなに必要ですか、struct?」

彼は、いわゆるSIに近いところにいて、ウェブアプリなどの開発などにも携わっていて、という立場。一方僕は3次元CAD関係だから、彼とは全く違う分野でやっている。二人ともプログラマでありながら、お互いに知らない分野をやっているので、こういう情報交換はとても面白い。

「ほら、3次元の幾何演算をしようと思ったら、座標値(x,y,z)を格納したり演算したりしたいからさ、ベクトルクラスとか作るでしょ?doubleとかfloatでx,y,zのフィールドを持ってる単純なクラス。」

僕もビールを飲みながら説明を始めた。

最近は3次元測定機の応用がどんどん広まってきている。3次元測定とは、レーザーなどを用いて実物の形状データをスキャンしコンピュータに取り込む技術だ。この測定機から得られるのは点群データ、すなわち膨大な(x,y,z)座標値の列だ。

問題はこの点群データのサイズ(得られる座標値の数)だ。数百万点はザラで、大きいものは数千万点に及ぶ。まだデータサイズは増える傾向にあるようだし、土木関係になるとデータ量は簡単に億を超えてしまうと聞いている。

こういった分野の応用を視野に入れた場合、それらの座標値ひとつひとつをガベコレに管理されるオブジェクトとして扱うのは非現実的だ。あっという間にメモリを使い果たしてしまうし、パフォーマンスにも問題が出るだろう。しかしJavaにはstructがないので、ベクトルクラスを作ったらそれはヒープにnewされるオブジェクトになってしまう。これに対してC#には(.NETには)structがある。これが僕がJavaを選ばずにC#にした理由だ。

ちなみに、僕は簡単なメモリアロケータのようなものも自作している。ベクトルのような固定長structのコレクションに特化すれば、メモリをより効率的に使えるのではないかと考えたためだ。これが作れたのは、C#がunsafeコードを扱えるからである。unsafeキーワードを使えばC/C++のようにポインタを使って低位のプログラミングができる。

さらにいうと、Java演算子の多重定義が出来ない。これも幾何演算をしたい立場からは窮屈極まりない。やっぱり、ベクトルクラスを作ったら足し算や引き算は演算子でやりたいよね。

ひとしきり説明を終えると、彼も理解してくれたようだった。

「なるほど・・・。それは工夫すればJavaでも出来ないわけではないと思います。でも確かに、structでより自然に記述できるんならそのほうがいいですね。」

もちろん、C#には他にも優れた点がたくさんある。delegateラムダ式、yield return、LINQなど。それから、デスクトップアプリを開発する身としては .NET Framework が利用できることも嬉しい。しかし、何が決定的な理由かと聞かれれば、それはやっぱりstructだと思うのだ。

Javaは "The Network is The Computer" の標語の下に開発された言語である。

しかしC#には、コンピュータをコンピュータ(計算機)として使いたい、という層にも配慮がある。僕にとっては、そこがいい。


・・・と、ここまで書いたところで、ちょっとググッたら次の記事が見つかった。

 さて、私がC#に乗り換えた10の理由とは、「struct」「delegate」「property」「custom attribute」「thread」「interface」「virtualとoverride」「#if」「Visual Studio .NET」「Javaが嫌になった」である。以下にその詳細を示す。

特集 私がJavaからC#に乗り換えた10の理由(1/4) - @IT

この方も最初の理由に struct を挙げていますね。