实验一利用子集法构造DFA教学内容文档格式.docx
《实验一利用子集法构造DFA教学内容文档格式.docx》由会员分享,可在线阅读,更多相关《实验一利用子集法构造DFA教学内容文档格式.docx(42页珍藏版)》请在冰豆网上搜索。
![实验一利用子集法构造DFA教学内容文档格式.docx](https://file1.bdocx.com/fileroot1/2022-10/25/47564eb3-ed9b-46ca-bf99-7abbeabbb471/47564eb3-ed9b-46ca-bf99-7abbeabbb4711.gif)
usingnamespacestd;
structedge{
intstart,end;
charc;
}
E[100],Ekong[100];
//E保存所有的边,Ekong保存转换字符为空的边
structState{
intH[100];
//状态集合
intcount;
//状态集合中的元素个数
intflag;
//是否是接受状态
intmark;
//状态编号
};
intn;
//n:
边数
intnk=0;
//空字符转换的边数
intfirst,accept;
//开始状态,接受状态
charalpha[100];
//输入字母表,#代表空串
intnumof_char=0;
//字母表中的字符个数
intuseof_char[256];
//该转换字符是否用过
intf[200];
//状态属性标志:
0表示始态,1表示接受态,-1表示中间态
StateDFA[100];
//DFA状态集
intuseof_DFA[100];
//标志构造出来的状态是否已存在
intnumof_Dtran=0;
//最后得到的DFA中的状态数
charDtran[100][100];
//DFA状态转换表
voidinput()
{
inti,s,e;
charch;
cout<
<
"
请输入转换的有向边数n:
endl;
cin>
>
n;
请输入NFA的开始状态:
first;
请输入NFA的接受状态(输入-1结束):
memset(f,-1,sizeof(f));
memset(useof_char,0,sizeof(useof_char));
f[first]=0;
accept;
while(accept!
=-1)
f[accept]=1;
cin>
请输入NFA,起点,终点,转换字符('
#'
表示空字符):
intk=0;
for(i=0;
i<
i++)
s>
e>
ch;
E[i].start=s;
E[i].end=e;
E[i].c=ch;
if(ch!
='
&
!
useof_char[ch])
{
alpha[numof_char++]=ch;
useof_char[ch]=1;
}
if(ch=='
)
Ekong[nk].start=s;
Ekong[nk].end=e;
Ekong[nk].c=ch;
nk++;
Statemove(StateT,chars)//c!
Statetemp;
temp.count=0;
temp.mark=T.mark;
inti,j=0,k=0;
T.count;
j=0;
while(j<
n)
if(E[j].start==T.H[i]&
E[j].c==s)
{temp.H[temp.count++]=E[j].end;
j++;
returntemp;
voidarriveBynone(intt,intresult[],int&
num)//搜索状态t通过一个或多个空字符到达的状态,结果存在result中
intm=0;
num=0;
stack<
int>
S;
S.push(t);
intj;
while(!
S.empty())
j=S.top();
S.pop();
m=0;
while(m<
nk)
if(Ekong[m].start==j)
result[num++]=Ekong[m].end;
S.push(Ekong[m].end);
m++;
boolcheck(inti,StateT)//判断状态i是否在T中
for(j=0;
j<
j++)
if(T.H[j]==i)
returntrue;
returnfalse;
Stateclosure(StateT)//求闭包
STACK;
inti,j,k;
STACK.push(T.H[i]);
temp.H[i]=T.H[i];
temp.count=T.count;
while(!
STACK.empty())
{
intt=STACK.top();
STACK.pop();
//搜索状态t通过一个或多个空字符到达的状态
intsearch_result[100];
intnum;
arriveBynone(t,search_result,num);
for(j=0;
num;
if(!
check(search_result[j],temp))
temp.H[temp.count++]=search_result[j];
STACK.push(search_result[j]);
for(k=0;
k<
temp.count;
k++)
if(f[temp.H[k]]==1)
temp.flag=1;
break;
if(f[temp.H[k]]==0)
temp.flag=0;
break;
sort(temp.H,temp.H+temp.count);
numof_Dtran;
if(temp.count!
=DFA[i].count)
continue;
sort(DFA[i].H,DFA[i].H+DFA[i].count);
DFA[i].count;
if(DFA[i].H[j]!
=temp.H[j])
if(j>
temp.mark=DFA[i].mark;
intcheck_inDFA()//检查DFA中是否存在未被标记的状态,有则返回标号,否则返回-1
inti;
for(i=0;
useof_DFA[i])
returni;
return-1;
boolcheck_whetherin_DFA(StateT)
inti,j;
sort(T.H,T.H+T.count);
if(T.count!
=T.H[j])
returntrue;
if(i>
=numof_Dtran)
returnfalse;
else
voidchild_method()
intm,n;
for(m=0;
m<
100;
m++)
for(n=0;
n<
n++)
Dtran[m][n]='
;
for(m=0;
DFA[m].flag=-1;
StateS0,U;
S0.flag=0;
S0.count=1;
S0.H[0]=first;
StateT;
T=closure(S0);
T.mark=0;
T.flag=0;
DFA[numof_Dtran++]=T;
memset(useof_DFA,0,sizeof(useof_DFA));
intj=check_inDFA();
intk;
while(j!
useof_DFA[j]=1;
for(k=0;
numof_char;
U=closure(move(DFA[j],alpha[k]));
//ifU不在DFA中
check_whetherin_DFA(U))
{U.mark=numof_Dtran;
DFA[numof_Dtran++]=U;
Dtran[DFA[j].mark][U.mark]=alpha[k];
j=check_inDFA();
voidprint()
cout<
:
DFA[i].H[j]<
"
if(DFA[i].flag==1)
此为DFA的接受状态"
if(DFA[i].flag==0)
此为DFA的开始状态"
{if(Dtran[i][j]!
{cout<
->
By"
Dtran[i][j]<
voidjudge(stringch)
inti,j,k;
intnum=ch.length();
Statetemp;
k=0;
if(Dtran[k][j]==alpha[i])
temp=DFA[j];
k=j;
break;