发布网友
共2个回答
热心网友
//我有一个程序,用户输入表达式计算结果的,也许能帮得上忙。
//不过它只能输入整数,小数可以用(xxx/1000……)代替。
#include<stdio.h>
#include<stdint.h>
#include<stdbool.h>
#define ITEM_LN0
#define STR_LN0 256
typedef enum //定义条目类型枚举
{
TYPE_NULL = 0,
TYPE_NUMBER,
TYPE_SYMBOL,
}item_type_t;
typedef enum//定义运算符类型枚举
{
SYM_NULL = 0,
SYM_ADD,
SYM_SUB,
SYM_MUL,
SYM_DIV,
}item_symbol_t;
typedef struct//定义条目结构体
{
//bool isExist; //存在
item_type_t item_type; //条目类型(数字、符号、空)
item_symbol_t item_symbol; //符号类型(加、减、乘、除、空)
int item_level; //括号级别
float num; //数值
}item_t;
item_t items[ITEM_LN0]; //定义条目表
char str[STR_LN0]; //定义临时字符串
int currentLevel; //括号级别临时寄存器
int itemsLength; //条目表长度
bool prevIsNum; //上一字符是数字 标志
//计算某一个符号及其邻域
void carculate(int In)
{
int i;
switch(items[In].item_symbol)//计算前后条目
{
case SYM_ADD:
items[In - 1].num += items[In + 1].num;
break;
case SYM_SUB:
items[In - 1].num -= items[In + 1].num;
break;
case SYM_MUL:
items[In - 1].num *= items[In + 1].num;
break;
case SYM_DIV:
{
if(items[In + 1].num == 0.0)
{
printf("除数为零\n");
return;
}
items[In - 1].num /= items[In + 1].num;
}
break;
}
for(i = In;i < itemsLength; i ++) //移动
{
items[i] = items[i + 2];
}
itemsLength -= 2;
i = items[In - 2].item_level;
if(items[In].item_level > i);//获取新条目两边的级别最大值
i = items[In - 2].item_level;
//如果该数字两边的运算符级别都比该数字低,就降低数字级别
//以两边最高的为准。
if(items[In - 1].item_level > i)
items[In - 1].item_level = i;
}
main()
{
int i;
currentLevel = 0;
prevIsNum = false;
//CurrentItem.item_type = TYPE_NULL;
for(i = 0;i < ITEM_LN0;i ++) //初始化条目数组
{
//items[i].isExist = false;
items[i].item_symbol = SYM_NULL;
items[i].item_type = TYPE_NULL;
items[i].item_level = 0;
items[i].num = 0;
}
//items[0].isExist = true;//设置首个为空条目
i = 0;
while(1) //带空格扫描字符串
{
str[i] = getchar();
if(str[i] == '\0' || str[i] == '\n')
{
str[i] = '\0';
break;
}
i ++;
}
i = 0;
itemsLength = 1;//从1号开始,设置条目信息
while(str[i] != '\0')
{
if(str[i] >= '0' && str[i] <= '9')//如果是数字
{
if(prevIsNum)//如果先前是数字,就在原基础上累加
{
items[itemsLength - 1].num = items[itemsLength - 1].num * 10 + str[i] - '0';
}
else
{
items[itemsLength].num = str[i] - '0'; //新建数字条目
items[itemsLength].item_level = currentLevel;
items[itemsLength].item_type = TYPE_NUMBER;
prevIsNum = true;
itemsLength ++;
}
}
else if(str[i] == '+')
{
items[itemsLength].item_level = currentLevel;//新建符号条目
items[itemsLength].item_type = TYPE_SYMBOL;
items[itemsLength].item_symbol = SYM_ADD;
prevIsNum = false;
itemsLength ++;
}
else if(str[i] == '-')
{
items[itemsLength].item_level = currentLevel;
items[itemsLength].item_type = TYPE_SYMBOL;
items[itemsLength].item_symbol = SYM_SUB;
prevIsNum = false;
itemsLength ++;
}
else if(str[i] == '*')
{
items[itemsLength].item_level = currentLevel;
items[itemsLength].item_type = TYPE_SYMBOL;
items[itemsLength].item_symbol = SYM_MUL;
prevIsNum = false;
itemsLength ++;
}
else if(str[i] == '/')
{
items[itemsLength].item_level = currentLevel;
items[itemsLength].item_type = TYPE_SYMBOL;
items[itemsLength].item_symbol = SYM_DIV;
prevIsNum = false;
itemsLength ++;
}
else if(str[i] == '(')
{
currentLevel ++; //改变括号级别
}
else if(str[i] == ')')
{
currentLevel --;
if(currentLevel < 0)
{
printf("括号匹配错误\n");
return;
}
}
else
{
prevIsNum = false;
}
i ++;
}
if(currentLevel != 0)//检查括号匹配
{
printf("括号匹配错误\n");
return;
}
if((itemsLength & 1) != 0)//检查条目数
{
printf("表达式格式错误\n");
return;
}
//items[itemsLength].isExist = true;
itemsLength ++;//设置末尾空条目
for(i = 1;i < itemsLength - 1;i ++)//排除首尾空条目,检查正确性
{
if( //如果表达式为数字符号交替
(items[i].item_type == TYPE_NUMBER && (i & 1) != 0) ||
(items[i].item_type == TYPE_SYMBOL && (i & 1) == 0)
)
{
}
else
{
printf("表达式格式错误\n");
return;
}
}
do//不断查找最大级别运算符,先乘除后加减,从前面开始,依次运算
{
currentLevel = 0;
for(i = 1;i < itemsLength - 1;i ++)
{
if(items[i].item_level > currentLevel)
currentLevel = items[i].item_level;//寻找最大级别运算符
}
for(i = 1;i < itemsLength - 1;i ++)//锁定该最大级别乘除运算符的位置
{
if( items[i].item_level == currentLevel &&
items[i].item_type == TYPE_SYMBOL &&
(items[i].item_symbol == SYM_MUL || items[i].item_symbol == SYM_DIV)
)
break;
}
if(i != itemsLength - 1)//如果该运算符存在
carculate(i);
else//否则寻找加减
{
for(i = 1;i < itemsLength - 1;i ++)//锁定该最大级别加减运算符的位置
{
if( items[i].item_level == currentLevel &&
items[i].item_type == TYPE_SYMBOL &&
(items[i].item_symbol == SYM_ADD || items[i].item_symbol == SYM_SUB)
)
break;
}
if(i != itemsLength - 1)//如果该运算符存在
carculate(i);
}
}while(itemsLength > 3);//当不止一个条目时
printf("%f",items[1].num);//
}
热心网友
??什么鬼,用户输入算法,这种操作学校也有教??