タブが表現する幅は、環境によって違う。プログラマはそのことをよく認識し、タブの幅(桁数の設定)が変わっても、なるべくインデントが崩れないようにソースコードを書くべきである。それがソースコードの「読者」に対するマナーだろう。
といっても、それほど難しいことではない。一部の例外を除き、基本的にはスペースとタブを混在させないようにすればよい。
例えば、インデントが4桁の行はスペース、8桁の行はタブを使うといったことはよくない。タブが8桁(程度)であることを「読者」に強要するからである。
また、1行のインデントの中にタブとスペースを混在させるのもよくない。幅が固定のものと可変のものを合わせると「中途半端な可変」になり、崩れの原因となる。
ただし、この「混在させない」というルールには例外がある。
実は、タブを使ったインデントには、
スペースを使うべき場面というのがあるのだ。
★
ソースコードのインデントでは、プログラムの処理的に意味のあるまとまりを「段落」とみなし、その段落をまとめて段下げする。段落の中に段落を作るような場合には、どんどん下げていくので、「階層」のようになる。
前編
で例に挙げたソースでいえば、関数や「if」、「for」の後の括弧 { ... } の中のような、いわゆる「ブロック」がひとつの段落である。
一方、段落とは無関係なところでインデントが必要なこともある。
行が長くなりすぎたのでやむをえず改行するとか、単にソースを読みやすくするために改行するようなことがあるだろう。このような便宜的な改行でできた行は、段落としては直前の行と同じ階層に属する。しかしながら、直前の行よりも深くインデントすることが多い。
このようなインデントでは、段落の階層が下がるわけではないので、ここでは「階層」と区別して「調整」と呼ぶことにしよう。
例えば、
1: void func2( int a, // 階層0
2: int b, // 階層0 + 調整12
3: int c ){ // 階層0 + 調整12
4: if( a == 1 && // 階層1
5: b == 2 && // 階層1 + 調整4
6: c == 3 ){ // 階層1 + 調整4
7: int d = a + b + c; // 階層2
8: } // 階層1
9: } // 階層0
というソースがあったとする(※1)。
1行目にはインデントがない。段落の階層の数は0である。
2行目は、1行目の続きを便宜的に改行しているだけなので、やはり階層はない。ただし、「int b」を1行目の「int a」の位置に揃えるために「調整」をしている。3行目も同様。
4行目からは、関数「func2」のブロックの中に入るので、階層が1つ下がる。
5行目も便宜的な改行なので階層は4行目と同じく1である。ただし、「b == 2」をすぐ上の「a == 1」にそろえるために、4桁分の「調整」が続いている。6行目も同様。以下省略。
ここで、インデントを作るときのルールは、
1. 行の先頭から、「階層」の数だけタブを打つ
2. 更に「調整」をしたい場合には、スペースを打つ
である。タブが先でスペースが後である。その順番が逆であってはならない(※2)。
例えば、上記の5行目を書くときには、タブを1つだけ打ち、それ以後はスペースを4回打つのである。
タブを「→」、スペースを「-」で表現すると、次のようになる。
1: void func2( int a, // 階層0
2: ------------int b, // 階層0 + 調整12
3: ------------int c ){ // 階層0 + 調整12
4: →if( a == 1 && // 階層1
5: →----b == 2 && // 階層1 + 調整4
6: →----c == 3 ){ // 階層1 + 調整4
7: →→int d = a + b + c; // 階層2
8: →} // 階層1
9: } // 階層0
このようにすれば、タブの幅を変更しても、
階層内の位置が崩れることはない(※3)。
現実には、「調整」の一部または全部をタブにしているソースをよく見かける。当然ながら、タブの桁数を変更すると崩れてしまう。ソースを読みやすくするはずの改行が、逆にソースを読みにくくしてしまうとは、皮肉なものである。
★
ここまで、インデントについて考えてきたが、インデント以外の場所でも、縦にコードを揃える必要があるようなところでは、タブは使わないほうがよい。
タブという特殊な文字は常に意識して、取り扱いには注意が必要である。
プログラミング向けの
エディタ
には、タブを目に見える形で表示できるものが多い。もし自分のエディタの画面にタブが表示されないようだったら、表示することができないかどか、設定等を確認してみるといいだろう。
※1
ここでは便宜上、タブの代わりに全角スペースを使用。なお、HTML の PRE タグが使えることが判明したので、今回から使用している。環境によってはきちんと見えないかもしれないが。。。
※2
タブの左(前)にスペースがくることはない。スペースに限らず、タブの左にはいかなる文字もないほうがよい。つまり、行頭以外にはタブを使わないということである。本文の例でいえば、コメント「//」の前などにタブを入れたくなるが、スペースにすべき。そうしないと、コメントの開始位置が縦に揃わなくなる(もっとも、揃える必要がない場合はタブを入れてもかまわないのだが)。
※3
階層をまたがって縦に並べるようなことをしていれば、ずれてしまう(上記の例で言えば、縦に並んだコメント「//」の部分がずれてしまう)のだが、そのような記述が必要なケースは稀だろう。
スティーブ マコネル
日経BPソフトプレス (2005/03)
売り上げランキング: 4,432
石原 直樹 河村 嘉之 丸の内 とら 米持 幸寿 日経ソフトウエア
日経BP社 (2006/03/09)