用C语言采用模拟DFA算法编写一个扫描器
用C语言采用模拟DFA算法编写一个扫描器
/*
第一章:相关知识
DFA定义:一个确定的有穷自动机(DFA)M是一个五元组:M=(K,Σ,f,S,Z)其中
① K是一个有穷集,它的每个元素称为一个状态;
② Σ是一个有穷字母表,它的每个元素称为一个输入符号,所以也称Σ为输入符号字母表;
③ f是转换函数,是K×Σ→K上的映射,即,如 f(ki,a)=kj,
(ki∈K,kj∈K)就意味着,当前状态为ki,输入符为a时,将转换为下一个状态kj,
我们把kj称作ki的一个后继状态;
④ S ∈ K是唯一的一个初态;
⑤ Z??K是一个终态集,终态也称可接受状态或结束状态。
第二章:题目
用C语言采用模拟DFA算法编写一个扫描器(词法分析器)用来识别:
由任意个a或b开始后接aa再自加或自减1的字符串,即正规式r=(a|b)*aa(+|-)1描述的语言L(r)。
该词法分析器的任务:
(1)滤掉源程序中的无用成分,如空格;
(2)识别正规式r=(a|b)*aa(+|-)1描述的字符串。
从键盘读入或打开文件读入字符串,词法分析器读入字符ywe串后扫描源字符串,
若发现符合符合正规式r描述的字符串时,输出“yes”或“可接受”或“可识别”,
否则输出“no”或“不可识别”。
第三章:分析
第一节.
根据正规式(a|b)*aa(+|-)1,我们可以分析出 K有10个状态,也就是10个元素:
状态 s0:这时候已经识别的字符个数为0,也就是开始状态
状态 s1:从状态s0开始接受连续的字母 'a',转到状态 s1
状态 s2:从状态s0开始接受连续的字母 'b',转到状态 s2
状态 s3:从s2开始接受了一个字母 'a',转到状态 s3
状态 s4:从s3开始接受了一个字母 'a',转到状态 s4
状态 s5:如果s1已经连续接受了至少两个字母 'a',从s4开始接受一个符号 '+',转到状态 s5 。
或
从s4开始接受了一个符号 '+',转到状态 s5 。
状态 s6:如果s1已经连续接受了至少两个字母 'a',从s4开始接受一个符号 '-',转到状态 s6 。
或
从s4开始接受了一个符号 '-',转到状态 s6 。
状态 s7:从s5或s6开始接受了一个数字 '1',转到 s7。
状态 s8:从s7开始接受了一个字符串结束符号 '\0',转到状态s8。【这是成功状态】。
状态 s9:【这是出错状态】。
第二节.
根据正规式(a|b)*aa(+|-)1,我们可以分析出Σ包含的字母有:a,b,+,-,1
第三节.
根据正规式(a|b)*aa(+|-)1,我们分析出转换函数 f 有:
F[0]. s0 --(输入一个字母'a') --> s1
F[1]. s0 --(输入一个字母'b') --> s2
F[2]. s1 --(输入一个字母'a') --> s1
F[3]. s2 --(输入一个字母'b') --> s2
F[4]. s2 --(输入一个字母'a') --> s3
F[5]. s3 --(输入一个字母'a') --> s4
F[6]. 如果状态 s1中已经累积有至少两个字母'a'
s1 --(输入一个符号'+') --> s5
F[7]h. s4 --(输入一个字母'+') --> s5
F[8]. 如果状态 s1中已经累积有至少两个字母'a'
s1 --(输入一个符号'-') --> s6
F[9]. s4 --(输入一个字母'-') --> s6
F[10]. s5 --(输入一个数字'1') --> s7
F[11]. s6 --(输入一个数字'1') --> s7
F[12]. s7 --(输入一个字符串结束符'\0') --> s8(成功状态)
F[13]. 其他情况,统一进入状态 s9(出错状态)
第四节.
根据正规式(a|b)*aa(+|-)1,我们分析出【唯一的】初态S即K中的 s0
第五节.
根据正规式(a|b)*aa(+|-)1,我们分析出结束状态有两个,即K中的 s8(成功状态),s9(出错状态)
*/
#include
/*