后缀表达式及计算器
来源:互联网 发布:冲压模具设计软件 编辑:程序博客网 时间:2024/06/06 20:11
#include<stdio.h>#include<stdlib.h>#define MAX 100typedef char datatype ;//栈结构体typedef struct { datatype a[MAX] ; int size ;}sequence_stack ;void init(sequence_stack *) ;int empty(sequence_stack *) ;datatype read(sequence_stack *) ;void pop(sequence_stack *) ;void push(sequence_stack *,datatype) ;int is_operation(char ch) ;int priority(char ch) ;//中缀表达式转后缀表达式的函数void postfix(char* ,char*) ;double read_number(char *dest ,int *i) ;double answer(char *dest) ;void match(char *src) ;/*------------------------------初始化函数------------------------------*/void init(sequence_stack *s){ s->size = 0 ;}/*------------------------------判断是否为空栈------------------------------*/int empty(sequence_stack *s){ return s->size ? 0:1 ;}/*------------------------------读取栈顶元素------------------------------*/datatype read(sequence_stack *s){ if(empty(s)) { printf("read函数错误, 为空栈!!") ; exit(1) ; } return s->a[s->size-1] ;}void pop(sequence_stack *s){ if(empty(s)) { printf("pop函数错误, 为空栈!!") ; exit(1) ; } s->size-- ;}void push(sequence_stack *s ,datatype d){ if(s->size==MAX) { printf("push函数错误, 栈已满!!") ; exit(1) ; } s->a[s->size++] = d ;}/*------------------------------判断字符是否是操作符------------------------------*/int is_operation(char ch){ int f = 0 ; switch(ch) { case '+': case '-': case '*': case '/': f =1 ; break ; default: f =0 ; break ; } return f ;}/*------------------------------获得优先级------------------------------*/int priority(char ch){ int f =-1 ; switch(ch) { case '#': f = -1 ; break ; case '(': case ')': f = 0 ; break ; case '+': case '-': f = 1; break ; case '*': case '/': f =2 ; break ; default: break; } return f ;}/*-----------------------------中缀表达式转后缀表达式src存储的是中缀表达式dest存储的是后缀表达式分为4个部分:1.遇到数字字符怎么处理 将数字读出2.遇到运算字符的处理 用while读取栈顶,栈顶元素>=运算符 ,就出栈,直到退出循环,最后将运算符压入栈中3.遇到(的处理 将(压入栈中即4.遇到)的处理 运算字符不用判断优先级全部出栈,直到遇到(与它配对-----------------------------*/void postfix(char *src,char *dest){ //创建栈结构体 sequence_stack opt ; sequence_stack *p = &opt ; int i =0 ; int j =0 ; //一定要初始化栈 init(p) ; push(p,'#') ; while(src[i]!='#') { if(src[i]>='0'&&src[i]<='9') { while( (src[i]>='0'&&src[i]<='9')||src[i]=='.' ) dest[j++] = src[i++] ; } else if(is_operation(src[i])) { dest[j++] = ' ' ; while(priority(src[i]) <= priority( read(p) )) { dest[j++] = read(p) ; pop(p) ; } push(p,src[i]) ; i++ ; } else if(src[i]=='(') push(p,src[i++]) ; else if(src[i]==')') { while(read(p)!='(') { dest[j++] = read(p) ; pop(p) ; } if(read(p)=='(') pop(p) ; i++ ; } } while(empty(p)!=1) { dest[j++] = read(p) ; pop(p) ; } dest[j] ='\0' ;}/*-------------------------------从后缀表达式中读取数据-------------------------------*/double read_number(char *dest ,int *i){ double x = 0 ; int num =0 ; int j ; while(dest[*i]<'0'||dest[*i]>'9') (*i)++; while(dest[*i]>='0'&&dest[*i]<='9') { x = x*10+(dest[*i]-'0') ; (*i)++ ; } if(dest[*i]=='.') { (*i)++ ; while(dest[*i]>='0'&&dest[*i]<='9') { num++ ; x = x*10+(dest[*i]-'0') ; (*i)++ ; } } for(j=0 ;j<num ;j++) x=x/10 ; return x ;}/*---------------------------根据后缀表达式计算结果---------------------------*/double answer(char *dest){ double xs[50] ; int len = 0 ; int i = 0 ; while(dest[i]!='#') { if(dest[i]>='0'&&dest[i]<='9') xs[len++] = read_number(dest,&i) ; else if(is_operation(dest[i])) { switch(dest[i]) { case '+': xs[len-2] = xs[len-2]+xs[len-1] ; len-- ; i++ ; break ; case '-': xs[len-2] = xs[len-2]-xs[len-1] ; len-- ; i++ ; break ; case '*': xs[len-2] = xs[len-2]*xs[len-1] ; len-- ; i++ ; break ; case '/': xs[len-2] = xs[len-2]/xs[len-1] ; len-- ; i++ ; break ; } } else i++ ; } return xs[len-1] ;}/*----------------------------匹配表达式是否正确----------------------------*/void match(char *src){ int i =0 ; sequence_stack stack ; sequence_stack *p = &stack ; init(p) ; while(src[i]!='#') { //如果表达式中的不是下列字符 if( (is_operation(src[i])!=1&&src[i]!='('&&src[i]!=')' &&src[i]!='.') && ( src[i]<'0'||src[i]>'9') ) { printf("输入错误!!") ; exit(1) ; } switch(src[i]) { case '(': push(p,src[i]) ; break ; case ')': if(is_operation(src[i-1])||src[i-1]=='(') { printf("括号输入有误!") ; exit(1) ; } if(read(p)=='(') pop(p) ; else { printf("括号输入有误!") ; exit(1) ; } break ; case '+': case '-': case '*': case '/': if(src[i-1]=='('||is_operation(src[i-1])) { printf("运算符输入问题!"); exit(1) ; } break ; default:break ; }//switch i++ ; }}int main(){ char src[MAX] ;//中缀表达式 char dest[MAX] ;//后缀表达式 char ch ; int i =0 ; double n =0 ; while((ch=getchar())!='\n') { src[i++] = ch ; } src[i++] = '#' ; src[i] ='\0' ; printf("中缀表达式: %s\n",src) ; match(src) ; postfix(src,dest) ; printf("后缀表达式: %s\n",dest) ; n = answer(dest) ; printf("answer = %.2f\n",n) ; getchar() ; return 0 ;}
0 0
- 后缀表达式及计算器
- 计算器(后缀表达式)
- C++后缀表达式计算器
- 通过后缀表达式模拟计算器
- 计算器实现---中缀表达式转后缀表达式
- 计算器:中缀表达式转后缀表达式
- c++ 中缀表达式转后缀表达式 计算器
- 使用c语言实现后缀表达式计算器
- 制作计算器,包含后缀表达式的求法
- 后缀表达式的计算器Java实现
- java使用后缀表达式实现计算器
- 后缀表达式及应用
- java 逆波兰表达式 (后缀表达式) 计算器
- HDU1237简单计算器-中缀表达式-后缀表达式
- 简单计算器求值(中缀表达式转化成后缀表达式)
- 中缀表达式转后缀表达式之多项式计算器
- 中缀表达式转后缀表达式及后缀表达式的计算
- 后缀表达式求值及中缀表达式转后缀表达式
- 状态压缩dp入门
- ConcurrentHashMap总结
- 一些以前学习的Android知识的整理(3)
- jprofiler主要功能简介及内存泄漏分析示例
- 实验14——自定义服务器端验证
- 后缀表达式及计算器
- MySQL优化必须调整的10项配置
- Kd-tree的用法
- 如何让一个ListVIew按类型显示多种Item视图
- 文件的读取写入
- Java设计模式—代理模式
- 欢迎使用CSDN-markdown编辑器
- Leetcode 349. Intersection of Two Arrays
- 面试时说的Android消息机制