flex提供一个根据条件激活规则的机制。
假设有一条规则是这样的(有一个<sc>前缀):
<sc>{id} insertID(yytext);
那么只有当scanner在<sc>这个条件里的时候,这条规则才会有效。原本的情况是这样的:
{id} insertID(yytext);
scanner看见符合id的token就执行insertID(yytext)这条指令了。不需要任何的条件。
那么怎么进到条件里呢?
首先你要在lex定义文件的definitions区域(第一块区域)声明一个条件:
%s sc
或者
%x sc
%s声明的条件是inclusive条件,而%x声明的条件是exclusive条件。两者区别后文阐述。
然后你要用BEGIN指令来激活这个条件:
BEGIN(sc);
原理就是这么回事了。
那么inclusive条件和exclusive条件有什么区别呢?
如果,有一个inclusive条件被激活了,那么没有前缀条件的规则也会有效。就像承包鱼塘一样:其他的规则也被我inclusive条件承包啦!
如果,有一个exclusive条件被激活了,那么没有前缀条件的规则就什么事也没有,休假了。只有带着这一条exclusive条件前缀的规则才要忙活起来。
有一些注意事项:
<*>代表所有条件:也就是无条件了,规则在任何情况都会生效。
BEGIN(0)和BEGIIN(INITIAL)都是回到初始条件。
像sc这样的条件名字其实是整型,你也可以用一个整型变量来存储下来他的值。
当前的start condition是什么呢,YY_START(或者YYSTATE)会告诉你。