手撸词法分析器(C/C++)
- 一.背景
- 二.什么是词法分析器?
- 三.代码
- 四.思考
一.背景
这学期开设了编译原理,要求写个基本的词法分析器。所以博主就自己写了一份代码,也比较简单基础。
二.什么是词法分析器?
简单来说就是能识别基本的符号(+,-,*,/,),关键词(for ,while,return ,int ),数字等。这么说大家应该有个基本了解,那么我们如何写代码呢,这里有个思维图。
可以大致将单词分成这几类,然后进行判断即可。
三.代码
#include <stdio.h>
#include <string>
#include < fstream >
#include <iostream>
int scan_word(char* buff);
using namespace std;
char buf[102400] = { 0 };
char key[][20] = {"if","else","for","while","do","return","break","continue",
",",";","{","}","(",")",
"+","-","*","/",
"<","<=","=",">=","< ","*=","/=","+=","-=","++",
"int", "char", "float","double","unsigned char","unsigned int","void",
"main"
};
int main()
{
ifstream fin;
int i =0,j=0,k=0;
fin.open("demo.txt", ios::in);
char temp[20] = { 0 };
if (!fin.is_open())
{
cout << "读取文件失败" << endl;
return 1;
}
while ((buf[i++] = fin.get()) != EOF);
buf[i] = '\0';
while (j < i-2)
{
start:
if (buf[j] == 0x0a || buf[j] == 0x0d || isspace(buf[j]))
{
j++;
goto start;
}
//字母
else if ((buf[j] >= 65 && buf[j] <= 90) || (buf[j] >= 97 && buf[j] <= 122))
{
while ((buf[j] >= 65 && buf[j] <= 90) || (buf[j] >= 97 && buf[j] <= 122)|| ((buf[j] >= 48 && buf[j] <= 57))||buf[j]==95)
{
temp[k++] = buf[j++];
}
temp[k] = '\0';
k = 0;
scan_word(temp);
}
//数字
else if ((buf[j] >= 48 && buf[j] <= 57))
{
while (buf[j] >= 48 && buf[j] <= 57)
{
temp[k++] = buf[j];
j++;
}
if (buf[j] == '.')
{
temp[k++] = buf[j];
j++;
}
while (buf[j] >= 48 && buf[j] <= 57)
{
temp[k++] = buf[j];
j++;
}
temp[k] = '\0';
k = 0;
printf("\(51,\"\%s\"\)\n", temp);
//scan_word(temp);
}
//其他符号
else
{
if(buf[j]=='>'||buf[j]=='='||buf[j]=='<' || buf[j] == '+'|| buf[j] == '-' || buf[j] == '*'||buf[j] == '/')
{
if (buf[j + 1] == '=')
{
temp[0] = buf[j++];
temp[1] = buf[j++];
temp[2] = '\0';
}
if (buf[j + 1] == '+')
{
temp[0] = buf[j++];
temp[1] = buf[j++];
temp[2] = '\0';
}
else goto end;
}
else
{
end:
temp[0] = buf[j++];
temp[1] = '\0';
}
scan_word(temp);
}
}
}
int scan_word(char *buff)
{
for (int i = 0; i < 31; i++)
{
if (strcmp(buff, key[i]) == 0)
{
printf("\(%d,\"\%s\"\)\n",i,buff);
return 1;
}
}
printf("\(50,\"\%s\"\)\n", buff);
return 0;
}
四.思考
这只是一个简单的词法分析器,很多功能都不完善,你们也可以自己添加代码改善一下。