1. 实验题目
无符号浮点数由三部分构成,具体描述如下:
- 小数点前面是整数部分,有两种情况:1、如果后面没有小数点就是十进制整数,以19开头、后跟09的任意多个数字;2、单个的0;
- 小数部分,从小数点开始,是可选的,小数点后跟1到多个0~9的任意数字;
- 指数部分,从e开始,也是可选的,e后面跟上可选的+/-,后跟1到多个0~9的任意数字。
请根据以上描述设计识别无符号浮点数的有穷自动机,根据识别结果输出“Yes”或“no”,并可以给出出错的位置。
2. 状态转换图
3. 算法流程图
4. C 语言实现
#include<stdio.h>
#include<stdlib.h>
#define N 100 // 存放用户输入内容的字符数组的长度
int index=0; // 下一个字符的索引,代替指针
char str[N]; // 存放用户输入内容的字符数组
char sign[] = {'\n', ' ', '\t', '[', ']', '{', '}', '+', '-', '*', '/'}; // 空白、界符、运算符数组
void RecognizeId(char ch);
char GetNextChar();
int issign(char ch);
void exe();
void main()
{
exe();
}
// 获取识别内容的下一个字符
// 返回值:下一个字符
char GetNextChar()
{
index++;
return str[index];
}
// 判断字符是否为空白、界符、运算符
// ch:待判断字符
// 返回值:1(是)、0(不是)
int issign(char ch)
{
int i;
int length = sizeof(sign)/sizeof(sign[0]);
for(i=0;i<length;i++)
{
if(ch == sign[length]) return 1;
}
return 0;
}
// 完整的无符号浮点数判断过程
// ch:识别内容的首字符
void RecognizeId(char ch)
{
char state = '0'; //初始状态
while(state != '8' && state != '9') {
switch(state){
case '0': if ((ch >= 49)&&(ch <= 57)) state = '1'; //1-9,转状态 1
else if (ch == 48) state = '2'; //0,转状态 2
else state = '8'; //其他,转状态 8
break;
case '1': ch = GetNextChar(); //读取下一个输入字符
if ((ch >= 48)&&(ch <= 57)) state = '1'; //0-9,转状态 1
else if(ch == 'e') state = '5'; //e ,转状态 5
else if(ch == '.') state = '3'; //. ,转状态 3
else if(issign(ch)) state = '9'; //空白、界符、运算符,转 9
else state = '8'; //其他,转状态 8
break;
case '2': ch = GetNextChar(); //读取下一个输入字符
if(ch == '.') state = '3'; //. ,转状态 3
else state = '8'; //其他,转状态 8
break;
case '3': ch = GetNextChar(); //读取下一个输入字符
if ((ch >= 48)&&(ch <= 57)) state = '4'; //0-9,转状态 4
else state = '8'; //其他,转状态 8
break;
case '4': ch = GetNextChar(); //读取下一个输入字符
if ((ch >= 48)&&(ch <= 57)) state = '4'; //0-9,转状态 4
else if(ch == 'e') state = '5'; //e ,转状态 5
else if(issign(ch)) state = '9'; //空白、界符、运算符,转 9
else state = '8'; //其他,转状态 8
break;
case '5': ch = GetNextChar(); //读取下一个输入字符
if ((ch >= 48)&&(ch <= 57)) state = '7'; //0-9,转状态 7
else if(ch == '+' || ch == '-') state = '6'; //+/-,转状态 6
else state = '8'; //其他,转状态 8
break;
case '6': ch = GetNextChar(); //读取下一个输入字符
if ((ch >= 48)&&(ch <= 57)) state = '7'; //0-9,转状态 7
else state = '8'; //其他,转状态 8
break;
case '7': ch = GetNextChar(); //读取下一个输入字符
if ((ch >= 48)&&(ch <= 57)) state = '7'; //0-9,转状态 7
else if(issign(ch)) state = '9'; //空白、界符、运算符,转 9
else state = '8'; //其他,转状态 8
break;
}
}
if(state == '9') printf("这是一个无符号浮点数\n");
else printf("这不是一个无符号数, 错误位置在%d这个位置\n", index+1);
fflush(stdin);
}
// 总执行函数,实现循环控制是否继续识别
void exe()
{
int iscontinue=0; // 是否继续识别标志位
int i=0;
printf("这是一个识别无符号浮点数的有穷自动机程序\n");
while(1)
{
printf("请输入您要测试的无符号浮点数:");
scanf("%s", str);
RecognizeId(str[index]);
for(i=0;i<N;i++) str[i] = 0; // 完成一次识别后重置 str
printf("是否还要继续测试(1:继续 2:停止)");
scanf("%d", &iscontinue);
fflush(stdin); // 清空输入缓冲,防止上次的输入造成影响影响
index=0; // 完成一次识别后重置 index
if(iscontinue == 2) return;
}
}