#include <stdio.h>
#include <ctype.h>
#define SIZE 512
#define CR '/n'
char file[300]="input.txt";//用于接收输入输出文件名
//定义分界符
char singleword[50]="+-=#;<>";
FILE *fin; //指向输入文件的指针
void main(){
int returnvalue=0;
cmdinput();
returnvalue=scan(); //进行词法分析
if (returnvalue==1) printf("分析有错!The maxium length of token is 15 characters!/n");
else printf("分析成功!/n");
}
int scan()//词法分析函数
{
char ch,chk=0,id[15]; //ch为每次读入的字符,chk为引号、回车检查所用量,id用于保存识别出的单词
int i=1,j,n=0; //i,j为临时变量,n统计token个数
int flag; //检查一行内是否有两个引号,是为1,否为0
FILE *tmp; //用于存放文件读指针_IO_read_ptr的地址
fin=fopen(file,"r");
ch=getc(fin);
start:
while(ch!=EOF)
{
while (ch==' '||ch=='/n') //如果已经到达文件尽头或出现连续两个回车则结束
{
chk=ch;
ch=getc(fin);
if (ch==EOF) goto end;
else if(ch=='/n')
goto end;
else if(ch!='/n'&&chk!=' '&&chk!=34) //对回车的判定
{
printf("token[%d] is/t<CR>/n",i);
fseek(fin,-1L,1);
ch=getc(fin);
i++;
chk=0;
}
}
if (isalnum(ch)) //如果是字母或者数字,则进行标识符处理
{
id[0]=ch; j=1;
ch=getc(fin);
while(isalnum(ch)) //如果是字母数字则组合标识符;如果不是则标识符组合结束
{
id[j++]=ch; //组合的标识符保存在id中
ch=getc(fin); //读下一个字符
if(j>15)
goto error;
}
id[j]='/0'; //标识符组合结束
printf("token[%d] is/t",i);
puts(id);
}
else if (strchr(singleword,ch)>0) //分界符处理
{
id[0]=ch; id[1]='/0';
ch=getc(fin);//读下一个符号以便识别下一个单词
printf("token[%d] is/t",i); //输出单分界符符号
puts(id);
}
else if (ch==',') //单分符处理
{
ch=getc(fin);//读下一个符号以便识别下一个单词
i--;
}
else if (ch==34) //当遇到第一个引号时进行检测
{
tmp=fin->_IO_read_ptr; //保存当前文件读指针的位置以便恢复
while(1)
{
if(chk==34)
{
flag=1;break;
}
else if(chk=='/r'||chk=='/n')
{
flag=0;
break;
}
else
flag=0;
chk=getc(fin);
}
if (flag==0)
{
fin->_IO_read_ptr=tmp;
id[0]=34;id[1]='/0';
ch=getc(fin);
printf("token[%d] is/t",i);
puts(id);
i++;
goto start;
}
else
{
fin->_IO_read_ptr=tmp;
ch=getc(fin);
while(ch!=EOF)
{
while (ch==' '||ch==34||ch=='/n')
{
chk=ch;
ch=getc(fin);
if (ch==EOF) goto end;
if (ch!='/n'&&chk!=' '&&chk!=34)
{
printf("token[%d] is/t<CR>/n",i);
fseek(fin,-1L,1);
ch=getc(fin);
i++;
chk=0;
}
}
if (isalpha(ch)||isdigit(ch))
{
id[0]=ch; j=1;
ch=getc(fin);
while(isalnum(ch))
{
id[j++]=ch;
ch=getc(fin);
if(j>15)
goto error;
}
id[j]='/0';
printf("token[%d] is/t",i);
puts(id);
}
else if (strchr(singleword,ch)>0)
{
id[0]=ch; id[1]='/0';
ch=getc(fin);
printf("token[%d] is/t",i);
puts(id);
}
else if (ch==',')
{
ch=getc(fin);
i--;
}
i++;
flag=0;
goto start;
}
}
}
i++;
}
fclose(fin);//关闭输入文件
end: return(0); //返回主程序
error: return(1); //返回出错代码
}
void cmdinput() //输入函数
{
char buffer[SIZE]; //定义输入缓冲区大小
FILE *fp1;
fp1=fopen(file,"w");
printf("Command Line:/n");
printf("Input a blank line to exit!/n"); //输入一个空行以结束输入函数
gets(buffer);
while(fgets(buffer,SIZE,fp1)!=NULL||buffer[0]!=0)
{
fputs(buffer,fp1);
fputc(CR,fp1); //在每行后插入一个回车
gets(buffer);
}
fclose(fp1);
printf("Input end!/n/n");
}