なんとなく手作業で行っている<span>タグを付ける作業をパターン化してみます。
public class Hoge {
public static void main(String[] args) {
// コメント
System.out.println("Hello World!");
}
}
まず、ソースを始めから1文字ずつ読み込んでいきます。"p"→"u"→"b"→"l"→"i"→"c"→" "と読んで、" "を読み込んだので、単語が終わった事が分かります。単語がpublicという予約語なので<span class="keyword">を付けます。予約語でなかったら<span class="keyword">を付けないでおきます。その後に"c"があるのでまた単語が始まります。しばらくこれを繰り返します。"/"→"/"と読んだ所で、コメントが始まっていると分かります。行末まで読んで<span class="comment">を付けます。
基本的に、一文字読む→読んだ文字とその前に読み込んだ文字列を判別して何かする→一文字読む→、、、を繰り返しです。「読んだ文字とその前に読み込んだ文字列を判別して何かする」の部分が結構複雑になると予想されるので、普通にフラグで分けようとすると行き詰まりそうです。C#/C++のソースをHTMLに変換するツールCSharpToHTMLは簡単にする為にStateパターンを使っています。これは有効なので、私が作るものにも使わせてもらいます。以下にStateの遷移を図にします。Word、Other、QuoteのStateは、一文字読んだ時にとりうるStateなので黄色に塗ってあります。
これだけだとC#/C++のソースをHTMLに変換するツールCSharpToHTMLと同じになってしまうので、もう一つ二つ工夫します。
Stateの役割をはっきりさせます。
Stateを扱うConverterクラスは、Stateに読込んだ文字を1文字ずつ送ります。Stateは読込んだ文字に応じて、Stateが終わった事をConverterに通知します。クラス図は以下のような感じです。