K&Rを読もう(14) 演習 1-21 スマートタブ
GNUインデント
世の中には様々なインデント方式がある。その中でも最も奇妙なインデント方式がGNUであろうと思う。
最初にGNU方式を目にしたときはハァ?ナンダコレ?などと思ったが、今はそのインデント方式が少し理解できるようになった。
スマートタブ
さて、今回はGNUで使われているインデント方式であるスマートタブに変換せよという問題です。
「8個スペースが続いたら、tabに変換する」
という奇妙なインデント方式。tabとスペースを混在させて使っている所がポイント。
今回のソースはGNU方式で書いてみたぞ。
#include <stdio.h> #include <stdlib.h> // #define TAB "\t" // #define TAB ">-------" #define TAB "\033[1;30m>-------\033[0m" int main (void) { int c; int count = 0; while ((c = getchar ()) != EOF) { if (c == ' ') { if (++count >= 8) { printf (TAB); count = 0; } } else { for (; count > 0; count--) putchar (' '); if (c == '\t') printf (TAB); else putchar (c); } } exit (EXIT_SUCCESS); }
うっは。読めねぇ・・・。
さて、ソースは全てスペースで構成されているので、スマートタブに変換してみる。
% ./ex-1-21 < ex-1-21.c
#include <stdio.h>
#include <stdlib.h>
// #define TAB "\t"
// #define TAB ">-------"
#define TAB "\033[1;30m>-------\033[0m"
int
main (void)
{
int c;
int count = 0;
while ((c = getchar ()) != EOF)
{
if (c == ' ')
>-------{
>------- if (++count >= 8)
>------- {
>------- printf (TAB);
>------- count = 0;
>------- }
>-------}
else
>-------{
>------- for (; count > 0; count--)
>------- putchar (' ');
>------- if (c == '\t')
>------- printf (TAB);
>------- else
>------- putchar (c);
>-------}
}
exit (EXIT_SUCCESS);
}GNUインデント完成〜。
可視化するとGNUインデントの変態っぷりがよくわかると思う。
こいつら絶対頭おかしいよ!!
追記
本来の問題は、スペーシングを最小にしろ。という事なので、スペースの後にtabがあった場合の処理も追加したほうがいいと思う。
>-----
tabの長さは可変なので真面目にやると大変。