词法分析实验

本文介绍了一种基于有限自动机的词法分析程序设计方法,包括NFA到DFA的转换及DFA最小化等内容,提供了S语言词法分析的具体实现。

一、实验目的

通过设计、开发一个高级语言的词法分析程序,加深对课堂教
学内容(包括正规文法、正规表达式、有限自动机、NFA到DFA的
转换、DFA的最小化)的理解,提高词法分析方法的实践能力。

二、实验要求

(1)深入理解、掌握有限自动机及其应用;
(2)掌握根据语言的词法规则构造识别其单词的有限自动机的方
法;
(3)掌握NFA到DFA的等价变换方法、DFA最小化的方法;
(4)掌握设计、编码、调试词法分析程序的技术与方法,具体实现
S语言(见附录A)的词法分析程序。

三、实验原理

词法分析是编译过程的第一个阶段。它的任务是对输入的字符
串形式的源程序按顺序进行扫描,根据源程序的词法规则识别具
有独立意义的单词,并输出单词的序列。
有限自动机是描述程序设计语言单词结构的工具,而状态转换
图是有限自动机的比较直观的描述方法。根据程序设计语言的词
法规则构造描述该语言单词结构的有限自动机,获取识别各类单
词的形式模型,进而通过编程模拟该形式模型的运行,可实现词
《编译原理》实验指导书法分析程序。

四、实验步骤

(1)根据S语言的词法规则,总结S语言的单词种类与各类单词的结
构特征;
(2)设计描述S语言各类单词结构的状态转换图(即有限自动机
FA);
(3)对描述各类单词结构的状态转换图进行合并(将各状态转换图
的初始状态合并为一个唯一的初态,然后对状态重新编号),
构成一个能识别S语言所有单词的状态转换图(NFA)。
(4)对能识别所有单词的NFA进行确定化操作,将其转换成等价的
DFA;
(5)对DFA进行最小化操作;
(6)编写程序,模拟最小化DFA的运行,实现S语言的词法分析程序;
(7)撰写实验报告。

代码:

#include<stdio.h>
#include<string.h>


void Print();
void Scanner();

int syn;//存放单词的类型 
int p;

char ch;
int sum;//用来保存数字的值 
char program[200],token[10];
char *rwtab[9]={"begin","if","then",
                "else","while","do","Const"
                ,"Var","end"};
int m;              

bool isDigital(char ch)
{
    if(ch<='9'&&ch>='0')
        return true;
    else
        return false;
}

bool isAlpha(char ch)
{
    if(ch>='a'&&ch<='z'||ch>='A'&&ch<='Z')
        return true;
    else
        return false;
}




void Scanner()
{
    int num=0;
    for(m=0;m<10;m++)
    {
        token[m]=NULL;
    }
    m=0;
    ch=program[p++];

    while(ch==' '||ch=='\n'||ch=='\t')
    {
        ch=program[p++];
    }
    if(isAlpha(ch)){
        do{
            token[m++]=ch;
            ch=program[p++];
        }while(isAlpha(ch)||isDigital(ch));
        p--;
        syn=10;
        token[m++]='\0';
        for(int n=0;n<=8;n++)
        {
            if(strcmp(token,rwtab[n])==0)
            {
                syn=n+1;
                break;
            }
        }
        return;
    }
    else if(isDigital(ch))
    {
        sum=0;
        while(isDigital(ch))
        {
            sum=sum*10+ch-'0';
            ch=program[p++];
        }
        p--;
        syn=11;
        if(isAlpha(ch))
            syn=-1;
        return;
    }
    else
    {
        token[0]=ch;
        switch(ch)
        {
            case '<':ch=program[p++];
                    if(ch=='>')
                    {
                        syn=22;
                        token[1]=ch;
                    }
                    else if(ch=='=')
                        {
                            syn=18;
                            token[1]=ch;
                        }
                    else{
                        syn=19;
                        p--;
                    }
                    break;
            case '>':ch=program[p++];
                    if(ch=='=')
                    {
                        syn=21;
                        token[1]=ch;
                    }
                    else{
                        syn=20;
                        p--;
                    }           
                    break;
            case '=':ch=program[p++];
                    if(ch=='=')
                    {
                        syn=17;
                        token[1]=ch;
                    }
                    else{
                        syn=17;
                        p--;
                    }
                    break;
            case '+':syn=12;break;
            case '-':syn=13;break;
            case '*':syn=14;break;
            case '/':syn=15;break;
            case ';':syn=23;break;
            case '(':syn=24;break;
            case ')':syn=25;break;
            case ',':syn=26;break;
            case '#':syn=0;break;
            default:syn=-1;break;                   
        }
        return;
    }
}

void Print()
{
    if(syn==11)
        printf("<%d,%d>\n",syn,sum);
    else
        printf("<%d,%s>\n",syn,token);
}


int main()
{
    printf("输入词法分析串以#作为结束\n");
    do
    {
        ch=getchar();
        program[p++]=ch;
    }while(ch!='#');
    p=0;
    //printf("%s\n",program);
    do{
        Scanner();      
        switch(syn)
        {
            case -1:printf("wrong\n",token);break;
            default:Print();break;
        }
    }while(syn!=0&&syn!=-1);
    if(syn==0)printf("success");

}
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值