第032回_条件付字句解析器8_PISectionLexer_PITokenizer他
»
今回はPI_WORDの字句解析器PISectionLexerを実装します。
これまでの内容を理解していれば問題ないと思いますので、解説はほとんどしません。
これまでの内容を理解していれば問題ないと思いますので、解説はほとんどしません。
PISectionLexerの実装
■構文のおさらい
PI_WORD ::= (Char* - (Char* '?>' Char*)
Char ::= [#x1-#xD7FF] | [#xE000-#xFFFD] | [#x10000-#x10FFFF]
つまり、
PI_WORD ::= Char かつ "?>" を含まない文字列
です。
■実装Char ::= [#x1-#xD7FF] | [#xE000-#xFFFD] | [#x10000-#x10FFFF]
つまり、
PI_WORD ::= Char かつ "?>" を含まない文字列
です。
public class PISectionLexer extends MapSwitchLexer
{
private static final PISectionLexer m_instance = new PISectionLexer();
private PISectionLexer()
{
// 記号 Unicode 処理
// -----------------------------------------------------
// char 0001-003E PITokenizerへ
// ? 003F PITokenizer2へ
// char 0040-D7FF PITokenizerへ
// char E000-FFFD PITokenizerへ
// その他 UnkonownTokenを作成する
// EOF EofTokenを作成する
Init_MovePos pi1
= new Init_MovePos(new PITokenizer());
MovePos pi2
= new MovePos(new PITokenizer2());
Init_MovePos unknownTokenizer
= new Init_MovePos(new UnknownTokenizer());
EofTokenizer eof
= new EofTokenizer();
m_map.put('\u0001', '\u003E', pi1);
m_map.put('\u003F', pi2);
m_map.put('\u0040', '\uD7FF', pi1);
m_map.put('\uE000', '\uFFFD', pi1);
m_map.setOutOfRange(unknownTokenizer);
m_map.setEofFunctor(eof);
}
public static PISectionLexer getInstance()
{
return m_instance;
}
}
PITokenizerの実装
public class PITokenizer extends MultipleMapsSwitchTokenizer
{
private class PIWordTokenMaker implements Functor
{
public PIWordTokenMaker()
{
}
@Override
public Token tokenize(StringBuilder str, int pos)
{
return new PIWordToken();
}
}
protected final PIWordTokenMaker m_piWordMaker;
public PITokenizer()
{
super();
m_piWordMaker = new PIWordTokenMaker();
makeMap_A();
makeMap_B();
}
private void makeMap_A()
{
//A (1文字前は確定)
//
// 記号 Unicode 処理
// -----------------------------------------------------
// char 0001-003E 今の文字を確定する
// ? 003F 未確定でB
// char 0040-D7FF 今の文字を確定する
// char E000-FFFD 今の文字を確定する
// それ以外 PI_WORDを作成する
// EOF PI_WORDを作成する
//
// 処理1:今の文字を確定する
// 処理2:未確定でB
// 処理3:PI_WORDを作成する
LexicalMap map = new LexicalMap();
Update_MovePos proc1 = new Update_MovePos(this);
MovePos_MoveMap proc2 = new MovePos_MoveMap(1);
// proc3 = m_piWordMaker
map.put('\u0001', '\u003F', proc1);
map.put('?', proc2);
map.put('\u0040', '\uD7FF', proc1);
map.put('\uE000', '\uFFFD', proc1);
map.setOutOfRange(m_piWordMaker);
map.setEofFunctor(m_piWordMaker);
m_mapList.add(map);
}
private void makeMap_B()
{
//B (1文字前?で未確定)
//
// 記号 Unicode 処理
// -----------------------------------------------------
// char 0001-003D 1文字前、今の文字を確定してA
// > 003E PI_WORdを作成する
// char 003F-D7FF 1文字前、今の文字を確定してA
// char E000-FFFD 1文字前、今の文字を確定してA
// それ以外 1文字前を確定してPI_WORDを作成する
// EOF 1文字前を確定してPI_WORDを作成する
//
// 処理1:今の1文字前、今の文字を確定してA字を確定する
// 処理2:PI_WORDを作成する
// 処理3:1文字前を確定してPI_WORDを作成する
LexicalMap map = new LexicalMap();
UpdateRange_MovePos_MoveMap
proc1 = new UpdateRange_MovePos_MoveMap(0,1,0);
// proc2 = m_piWordMaker
UpdateRange_MovePos
proc3 = new UpdateRange_MovePos(m_piWordMaker, 1,1);
map.put('\u0001', '\u003D', proc1);
map.put('>', m_piWordMaker);
map.put('\u003F', '\uD7FF', proc1);
map.put('\uE000', '\uFFFD', proc1);
map.setOutOfRange(proc3);
map.setEofFunctor(proc3);
m_mapList.add(map);
}
}
PITokenizer2の実装
public class PITokenizer2 extends PITokenizer
{
private class EmptyPIWordTokenMaker implements Functor
{
public EmptyPIWordTokenMaker()
{
}
@Override
public Token tokenize(StringBuilder str, int pos)
{
m_tokenBuilder.initStart();
return new PIWordToken();
}
}
private final EmptyPIWordTokenMaker m_emptyPiWordMaker;
public PITokenizer2()
{
super();
m_emptyPiWordMaker = new EmptyPIWordTokenMaker();
m_index = 2;
makeMap_C();
}
private void makeMap_C()
{
//C (tokenBuilder.initStartしていない、1文字前?で未確定)
//
// 記号 Unicode 処理
// -----------------------------------------------------
// char 0001-003D 初期化、1文字前、今の文字を確定してA
// > 003E 初期化、空のPI_WORdを作成する
// char 003F-D7FF 初期化、1文字前、今の文字を確定してA
// char E000-FFFD 初期化、1文字前、今の文字を確定してA
// それ以外 初期化、1文字前の文字を確定して
// PI_WORDを作成する
// EOF 初期化、1文字前の文字を確定して
// PI_WORDを作成する
//
// 処理1:初期化、1文字前、今の文字を確定してA
// 処理2:初期化、空のPI_WORdを作成する
// 処理3:初期化、1文字前の文字を確定してPI_WORDを作成する
LexicalMap map = new LexicalMap();
InitUpdateRange_MovePos_MoveMap
proc1 = new InitUpdateRange_MovePos_MoveMap(0,1,0);
// proc2 = m_emptyPiWordMaker
InitUpdateRange_MovePos
proc3 = new InitUpdateRange_MovePos(m_piWordMaker,1,1);
map.put('\u0001', '\u003D', proc1);
map.put('>', m_emptyPiWordMaker);
map.put('\u003F', '\uD7FF', proc1);
map.put('\uE000', '\uFFFD', proc1);
map.setOutOfRange(proc3);
map.setEofFunctor(proc3);
m_mapList.add(map);
}
}
コメント
コメントを投稿する
SpecialPR