/*前段时间在编译原理实验上写了一个PL0语言单词的词法分析程序,把源代码付上,供初学者参考。也欢迎大侠们提出宝贵的意见*/
#include <iostream>
#include <fstream>
#include <string>
using namespace std;
//设置单字符符号
char symbol[] = {'+','-','*','/','(',')','=',',','.','#',';'};
//设置单字符名称
string ssym[] = {"plus","minus","times","slash","lparen","rparen","eql","comma","peroid","neg","semicolon"};
//设置保留字
string word[] = {"begin","call","const","do","end","if","odd","procedure","read","then","var","while","write"};
//设置保留字符号
string wsym[] = {"beginsym","callsym","constsym","dosym","endsym","ifsym","oddsym","procsym","readsym","thensym","varsym","whilesym","writesym"};
ifstream fin("in.txt");
ofstream fout("result.txt");
void judgeWord(string str);//搜索当前符号是否为保留字
int judgeSymbol(char ch);//搜索当前符号是否为单字符符号
void getsym();//词法分析,获取一个符号
int main(){
getsym();//词法分析,获取一个符号
return 0;
}
void getsym(){
char ch;
ch = fin.get();
while(ch != '#'){
if(ch>='a' && ch<='z'){//名字或保留字以a..z开头
string strTemp = "";
do{
strTemp = strTemp + ch;
ch = fin.get();
} while(ch>='a' && ch<='z' || ch>='0' && ch<='9');
judgeWord(strTemp);//搜索当前符号是否为保留字
}
else{
if(ch>='0' && ch<='9'){//检测是否为数字:以0..9开头
double num = 0.0;
do{
num = 10 * num + ch - '0';//将形如:"12345"的字符串装换车long类型的12345
ch=fin.get();
}while(ch>='0' && ch<='9');
long div = 1;
if (ch == '.'){ //实型数的判断
ch=fin.get();
while(ch>='0' && ch<='9'){
div = div * 10;
num = num + static_cast<double>(ch-'0') / div;//将形如:"0.345"的字符串装换车double类型的0.345;
ch=fin.get(); //使用static_cast<double>强制装换成double.
}
}
cout << "[ number , " << num <<" ]/n"; //显示number;
}
else{
if (ch == ':'){//检测赋值符号
string strTemp = "";
strTemp = strTemp + ch;
ch = fin.get();
if (ch == '='){
strTemp = strTemp + ch;
cout << "[ becomes , " << strTemp <<" ]/n"; //显示赋值号:":="
}
else{
cout << "[ notBecomes , " << strTemp <<" ]/n"; //不能识别的符号
}
ch = fin.get();
}
else{
if (ch == '<'){//检测小于或小于等于符号
string strTemp = "";
strTemp = strTemp +ch;
ch = fin.get();
if (ch == '='){
strTemp = strTemp + ch;
cout << "[ leq , " << strTemp <<" ]/n"; //显示:"<="
}
else{
cout << "[ less , " << strTemp <<" ]/n"; //显示:"<"
}
ch = fin.get();
}
else{
if (ch == '>'){//检测大于或大于等于符号
string strTemp = "";
strTemp = strTemp +ch;
ch = fin.get();
if (ch == '='){
strTemp = strTemp +ch;
cout << "[ geq , " << strTemp <<" ]/n"; //显示:">="
}
else{
cout << "[ gtr , " << strTemp <<" ]/n"; //显示:">"
}
ch = fin.get();
}
else{
if(judgeSymbol(ch) != -1) {
int i=judgeSymbol(ch);
cout << "[ " << ssym[i] << " , " << ch <<" ]/n"; //显示保留字符的类型
ch = fin.get();
}
else ch = fin.get();//忽略空格、换行
}
}
}
}
}
}
}
void judgeWord(string str){
int i = 0;
int numWord = 13; //保留字的个数为13个
for (i=0; i<numWord; i++){
if (str == word[i] ){
cout << "[ " << wsym[i] << " , " << str <<" ]/n"; //显示保留字的类型
break;
}
}
if (i == numWord){
cout << "[ ident , " << str <<" ]/n"; //否则为自定义的变量
}
}
int judgeSymbol(char ch){
int i = 0;
int numSymbol = 11; //单符号个数
for (i=0; i<numSymbol; i++){
if (ch == symbol[i]){
return i;
}
}
return -1; //匹配不成功
}