uehaj's blog

Grな日々 - GroovyとかGrailsとかElmとかRustとかHaskellとかReactとかFregeとかJavaとか -

コメントに何を書いてもいい」と思うのは、/**/については正しいが、//については正しくない

Groovyで「//」で日本語のコメントをつけていたところ、ソースをMacOSからWindowsに持ってきたらシンタックスエラーで動かなくなった。

なんでかなーと思ったら原因は以下の通り、

  • 元のソースはUTF-8で書いてあった
  • つまり全角文字1文字3バイト
  • 元のソースの改行コードはLFだった。
  • コメント行の行末に全角文字があった。
  • このとき、WindowsのデフォルトエンコーディングShift_JIS(正確にはMS932)なので、UTF8の3バイトをShift_JISで解釈しようとして、まず頭の2バイトは化けた。まあコメントだから化けても別にそれはいい。問題は、Shift_JISのデコーダが、残る1バイトと、//コメント行末のLFをペアで食って、1文字と解釈してしまうこと。この結果、改行が消え去ることになり、続く一行がコメントの一部として解釈され、シンタックスエラーでした。

この問題はJavaでもGroovyでも同様ですが、Javaのほうがエラーメッセージが親切でわかりやすい。さらに、Groovyの場合、ソースをそのまま「実行可能ファイル」と認識しているから、動かないと混乱の度合いが大きく、さらに対策として-encodingを毎回groovyコマンド実行時に指定するのは面倒。つまりよりシリアス。

教訓は、デフォルトエンコーディングとスクリプトのエンコーディングが異なるなら(1)文字コード変換するか(2)実行時に正しくencodingを指定せよ(3)スクリプトのコメントについて文字コードなんてこまけーこたあ良いんだよ、といいたい場合は、/**/を推奨。(or行末に空白でも入れとけ)