当前位置:文档之家› 词法分析程序的设计与实现

词法分析程序的设计与实现

词法分析程序的设计与实现
词法分析程序的设计与实现

实验一词法分析程序的设计与实现

一、实验内容

【实验目的和要求】

设计、编制、调试一个具体的词法分析程序,加深对词法分析原理的理解。

【实验内容】

通过对PL/0词法分析程序(GETSYM)的分析,并在此基础上按照附录A中给出的PL/0语言的语法描述,编写一个PL/0语言的词法分析程序。此程序应具有如下功能:输入为字符串(待进行词法分析的源程序),输出为单词串,即由(单词、类别)所组成的二元组序列。

有一定检查错误的能力,例如发现2A这类不能作为单词的字符串。

【实验环境】

Windows PC机,任何语言。

【提交内容】

提交实验报告,报告内容如下:

目的要求、算法描述、程序结构、主要变量名说明、程序清单、调试情况、设计技巧、心得体会。

提交源程序和可执行文件。

【学时】

4课时。

二、实验说明

词法分析程序的任务就是扫描源程序,依据词法规则识别单词并报告构词错误信息。通常将单词分为5种类型。

1)基本字:也叫关键字、保留字,是程序设计语言用来表示特定语法含义的一种标识符,如if、begin等。

2)运算符:如+、-、*、/、:=、>、<等。

3)标识符:用户定义的变量名、常数名、函数名等。不同的高级程序设计语言对关键字是否可以作为普通标识符有不同的要求,有的语言允许程序员使用关键字作为普通标识符,有的程序设计语言则不允许程序员将关键字用着普通标识符(如C/C++、Pascal等都不允许)。在允许程序员将关键字用作普通标识符的程序设计语言的编译器中,编译器必须具备能够区分一个标识符到底是关键字还是普通标识符的功能。

4)常数:如23、6等。

5)界符:如“,”、“;”、“(”、“)”、“.”等。

注意事项

●空格的作用仅仅是将一个个单词分割开来,源程序中的空格不具备别的语法意义,在语法分析及其后续阶段都没有任何作用,因此,词法分析的另一个工作是过滤空格。

●注释对整个源程序的编译也没有任何语法意义,只是为了便于阅读和交流,因此,有的编译程序的词法分析程序也负责过滤注释。

●输出的单词符号采用[单词类别,单词自身值]的二元组形式来表示。

●为了使扫描程序尽可能的高效,在进行词法分析程序的设计和实现时还需十分注意扫描程序结构的实际细节问题。

●用于间隔单词的空格和我们通常所说的键盘上的空格是不同的,这里的空格指的是所有能引起一个单词结束的字符,它们包括空格、制表或回车换行符。

●a*(b+c)这样的没有空格间隔的情况时要正确地识别出所有的单词

●123ab这样的字符串时,一般字符串的首字符必须为字母,不要将123识别为数字,将ab识别为标识符

转换图说明

程序代码参考

package cffx;

import java.io.FileInputStream;

import java.io.IOException;

import java.io.InputStreamReader;

import java.io.Reader;

@SuppressWarnings("unused")

public class shiyan1 {

static public Reader reader = null;

// 关键字

static public String[] keyWords = { "if", "else", "for", "while", "do", "return", "break", "continue" };

// 界符

static public String[] borders = { ",", ";", "{", "}", "(", ")" };

// 运算符

static public String[] arithmetic = { "+", "-", "*", "/" };

// 关系符1

static public String[] relation1 = { "<", "=", ">" };

// 关系符2

static public String[] relation2 = { "<=", ">=", "<>" };

static public boolean isOver = false;

//处理一个字母开头的词

static private char alphaprocess(char buffer) throws Exception { int i = -1;

StringBuffer sb = new StringBuffer();

char temp = buffer;

while (Character.isLetter(temp) || Character.isDigit(temp)) { sb.append(temp);

if((temp = (char) reader.read()) == -1) {

isOver = true;

}

}

if(!search(sb.toString(), 1)){

search(sb.toString(),2);

}

return temp;

}

//处理数字开头的词

static private char digitprocess(char buffer) throws Exception { StringBuffer sb = new StringBuffer();

char temp = buffer;

while(Character.isDigit(temp)){

sb.append(temp);

if((temp = (char) reader.read()) == -1) {

isOver = true;

}

}

search(sb.toString(), 3);//处理一个数字

return temp;

}

//其他字符

static private char otherprocess(char buffer) throws Exception { StringBuffer sb = new StringBuffer();

char temp = buffer;

sb.append(temp);

if((temp = (char) reader.read()) == -1) {

isOver = true;

}

if(search(sb.toString(), 4)){return temp;}//界符

else if(search(sb.toString(), 5)){return temp;}//运算符

else if(search(sb.toString(), 6)){return temp;}//关系符1

sb.append(temp);

if(search(sb.toString(), 7)){

if((temp = (char) reader.read()) == -1) {

isOver = true;

}

}

return temp;

}

static private boolean search(String buffer, int wordtype) {

int i = 0;

switch (wordtype) {

case 1://确定是否为保留字

for(int j=0;j

if(keyWords[j].equals(buffer)){

System.out.println(buffer+"保留字"+j);

return true;

}

}

return false;

case 2://标示符,直接打印

System.out.println(buffer+"标示符,长度"+buffer.length());

return true;

case 3://数字

System.out.println(buffer+"数字"+buffer.length());

return true;

case 4://是否界符

for(int j=0;j

if(borders[j].equals(buffer)){

System.out.println(buffer+"界符"+j);

return true;

}

}

return false;

case 5://是否运算符

for(int j=0;j

if(arithmetic[j].equals(buffer)){

System.out.println(buffer+"运算符"+j);

return true;

}

}

return false;

case 6://关系符号1

for(int j=0;j

if(relation1[j].equals(buffer)){

System.out.println(buffer+"关系符"+j);

return true;

}

}

return false;

case 7://关系符号1

for(int j=0;j

if(relation2[j].equals(buffer)){

System.out.println(buffer+"关系符"+j);

return true;

}

}

return false;

default:System.out.println(buffer+"未知");return false;

}

}

/**

* @param args

* @throws Exception

*/

public static void main(String[] args) throws Exception {

reader = new InputStreamReader(new FileInputStream("d://source.c"));

char cbuffer;

cbuffer = (char) reader.read();

while(!isOver){

if (Character.isLetter(cbuffer)) {

cbuffer=alphaprocess(cbuffer);

} else if (Character.isDigit(cbuffer)) {

cbuffer=digitprocess(cbuffer);

} else {

cbuffer=otherprocess(cbuffer);

}

}

}

}

相关主题
文本预览
相关文档 最新文档