精华内容
下载资源
问答
  • 算法设计与分析 实验报告 - PAGE 1 - 实验目的 掌握栈后进先出的特点 掌握栈的典型应用后缀表达式求值 实验内容 用键盘输入一个整数后缀表达式操作数的范围是09运算符只含*/而且中间不可以有空格使用循环程序从左向...
  • ////数字与运算符直接要有空格 //#include //#include //#include //#include //using namespace std; //char s[10000]; //stack<int> p; //long long x,y; //int main(){ ...// y=p.t
  • #include<stdlib.h> #include<stdio.h> struct node // 栈结构声明 { int data; // 数据域 struct node *next; // 指针域 }; typedef struct node stacklist; // 链表类型 typedef stacklist *link;...
  • 后缀表达式求值

    2014-08-22 23:59:59
    后缀表达式求值,练习堆栈,算法。大家需要可以参考下
  • 本文实例讲述了PHP实现基于栈的后缀表达式求值功能。分享给大家供大家参考,具体如下: 后缀表达式概述 后缀表达式,指的是不包含括号,运算符放在两个运算对象的后面,所有的计算按运算符出现的顺序,严格从左向右...
  • 后缀表达式求值

    2013-03-08 22:15:54
    用数据结构栈实现后缀表达式求值的问题 输入一个后缀表达式 可计算出它的
  • 后缀表达式求值cpp

    2012-06-06 13:55:37
    #include "stdio.h" #include "stdlib.h" typedef char DataType;//声明自定义数据类型 typedef struct snode//声明栈结点
  • 实现数据结构中后缀表达式值的c语言完整可运行代码。
  • 中缀表达式转后缀表达式求值

    千次阅读 2019-03-27 17:29:59
    刚开始想一鼓作气把整个过程全部实现,但白费了那几个小时,调试了半天也没做出来,后来我是通过先实现中缀表达式转化为后缀表达式,然后实现后缀表达式求值,然后将两块代码进行合成,刚才同学还笑着说:模块化...

    刚开始想一鼓作气把整个过程全部实现,但白费了那几个小时,调试了半天也没做出来,后来我是通过先实现中缀表达式转化为后缀表达式,然后实现后缀表达式的求值,然后将两块代码进行合成,刚才同学还笑着说:模块化编程。。。

     

    直接在代码中解释。

    中缀表达式转后缀表达式:

    # include <iostream>
    # include <string>
    # include <sstream>
    # include <cctype>                //程序中需使用isdigit()函数,目的在于判别字符是否为数字,将符号和数字区别开来
    using namespace std;
    struct sign                      //建立存储符号的结构体
    {
    	char sign;
    	int level;
    	struct sign *next_1;
    };
    class linkstack
    {
    private:
    	struct sign *top;
    public:
    	linkstack() { top = NULL; }   //无参构造函数,top头指针初始化为零
    	char push_out();              //将栈顶元素出栈
    	void push_in(char new_sign);  //给栈中添加新元素
    	char print_top();             //返回栈顶元素中的符号内容
    	int print_level();            //返回栈顶元素符号的优先级
    };
    int compare(char compared_sign)   //给每个符号赋予优先级
    {
    	int level;
    	switch (compared_sign) {
    	case '(':
    		level = -10; break;
    	case ')':
    		level = -10; break;
    	case '+':
    		level = 0; break;
    	case '-':
    		level = 0; break;
    	case '*':
    		level = 1; break;
    	default:                     //default要加上
    		level = 1; break;
    	}
    	return level;
    }
    char linkstack::print_top()
    {
    	char result;
    	result = top->sign;
    	return result;
    }
    int linkstack ::print_level()
    {
    	return top->level;
    }
    char linkstack::push_out()               //删除栈顶元素
    {
    	char char_result;
    	struct sign *p;
    	char_result = top->sign;
    	p = top;
    	top = top->next_1;
    	delete p;
    	return char_result;                  //删除后需要给sting对象b中追加,所以需要返回
    }
    void linkstack::push_in(char new_sign)
    {
    	struct sign *s;
    	s = new struct sign;                 //添加栈顶元素
    	s->sign = new_sign;
    	s->level = compare(new_sign);
    	s->next_1 = top;
    	top = s;
    }
    int main()
    {
    	int count = 0; double m;           //count用来记录符号栈中的个数,用top!=NULL也可以
    	string a,b;
    	cin >> a;                          //string对象a是转化前的,b是转换后的
    	linkstack one;
    	for (auto c = a.begin(); c != a.end(); c++) {          //从a的第一个元素开始扫描
    		if (isdigit(*c)) {
    			b.push_back(*c);  continue;            //如果是数字isdigit(*c)为真,就给b中追加,进行下一个循环
    		}
    		else {
    			if (*c != ')'&&count==0) {            //如果栈为空,直接加入栈顶元素
    				one.push_in(*c);
    				count++;                         //记录栈元素的个数
    				continue;                        //进行下一个循环
    			}
    			if (*c==')') {                      //进行括号中的运算
    				while (one.print_top()!= '(') {             //一直循环到栈顶元素不等于‘(’
    					b.push_back(one.print_top());           //将目前栈顶元素追加给b
    					one.push_out(); count--;                //追加完后,删除栈顶元素,个数减一
    				}
    				one.push_out(); count--;                   //最后记得还要把左括号删除,以避免对下一个运算影响
    				continue;
    			}
    			if (compare(*c) <= one.print_level()) {     //如果当前符号优先级小于栈顶元素的优先级(即上一个运算符)
    				b.push_back(one.print_top());           //将栈顶运算符元素追加给b
    				one.push_out();                         //紧跟着删除刚才的栈顶元素
    				one.push_in(*c);                        //将当前的运算符号压入栈
    				continue;                               //进行下一个循环
    			}
    			if (compare(*c)>one.print_level()) {        //如果当前运算符优先级大于栈顶元素(即前一个运算符)
    				one.push_in(*c); count++;               //直接压入栈,个数加一,并进行下一个循环
    				continue;
    			}
    		}
    	}
    	if (count) {                                        //如果栈不空则还剩余一个符号没有追加给b
    		b.push_back(one.print_top());                   //追加栈中剩余的符号
    		one.push_out();
    	}
    	cout << b << endl;
    	system("pause");
    	return 0;
    }
    

    后缀表达式求值:

    # include <iostream>
    # include <string>
    # include <sstream>                    //下边程序中从string类型到double中要用到,具体的用法在以前的博客中我有详细提及
    using namespace std;
    struct operate         
    {
    	double member;         
    	struct operate *next;
    };
    class new_linkstack
    {
    public:
    	new_linkstack() { top = NULL; }      //初始化,top为NULL;
    	void push_in(double x);              //将数字压入栈
    	double push_out();                   //删除栈顶元素
    	void print_result();                 //打印运算完后的结果,也就是最后的栈顶元素
    private:
    	struct operate *top;
    };
    void new_linkstack::push_in(double in_number)
    {
    	struct operate *s;
    	s = new operate;
    	s->member = in_number;
    	s->next = top;
    	top = s;
    }
    double new_linkstack::push_out()
    {
    	struct operate *p;
    	if (top == NULL)throw"下溢";
    	double out_member;
    	out_member = top->member; p = top;
    	top = top->next;
    	delete p;
    	return out_member;
    }
    void new_linkstack::print_result()
    {
    	cout << top->member << endl;
    }
    int main()
    {
    	double x, y, result,b;
    	string new_a;
    	cin >> new_a;
    	new_linkstack one;
    	for (auto c = new_a.begin(); c != new_a.end(); c++) {   //从头到尾扫描new_a中的元素
    		if (isdigit(*c)) {              //如果当前元素为数字,直接入栈
    			stringstream sstream;
    			sstream << *c;
    			sstream >> b;              //string类型到double类型的转换
    			one.push_in(b);
    			sstream.clear();           //将stringstream流清空
    		}
    		else {                         //如果当前元素为运算符
    			x = one.push_out();        //将前两个栈顶的元素取出 
    			y = one.push_out(); 
    			switch (*c)                //new_a中的运算符不能直接用来做运算
    			{
    			case '+':
    				result = x + y; one.push_in(result); continue;//运算完后,将当前运算结果压入栈,进行下一个循环
    			case '-':
    				result = y - x; one.push_in(result); continue;
    			case '*':
    				result = x * y; one.push_in(result); continue;
    			case '/':
    				result = y / x; one.push_in(result); continue;
    			}
    		}
    	}
    	one.print_result();               //打印最终结果
    	system("pause");
    	return 0;
    }

    这样就将一个大的问题分成了两个小的问题,下边的代码是我合成之后的:

    # include <iostream>
    # include <string>
    # include <cctype>
    # include <sstream>
    using namespace std;
    struct sign
    {
    	char sign;
    	int level;
    	struct sign *next_1;
    };
    struct operate
    {
    	double member;
    	struct operate *next;
    };
    class new_linkstack
    {
    public:
    	new_linkstack() { top = NULL; }
    	void push_in(double x);
    	double push_out();
    	void print_result();
    private:
    	struct operate *top;
    };
    class linkstack
    {
    private:
    	struct sign *top;
    public:
    	linkstack() { top = NULL; }
    	char push_out();
    	void push_in(char new_sign);
    	char print_top();
    	int print_level();
    };
    int compare(char compared_sign)
    {
    	int level;
    	switch (compared_sign) {
    	case '(':
    		level = -10; break;
    	case ')':
    		level = -10; break;
    	case '+':
    		level = 0; break;
    	case '-':
    		level = 0; break;
    	case '*':
    		level = 1; break;
    	default:                         
    		level = 1; break;
    	}
    	return level;
    }
    char linkstack::print_top()
    {
    	char result;
    	result = top->sign;
    	return result;
    }
    int linkstack::print_level()
    {
    	return top->level;
    }
    char linkstack::push_out()
    {
    	char char_result;
    	struct sign *p;
    	char_result = top->sign;
    	p = top;
    	top = top->next_1;
    	delete p;
    	return char_result;
    }
    void linkstack::push_in(char new_sign)
    {
    	struct sign *s;
    	s = new struct sign;
    	s->sign = new_sign;
    	s->level = compare(new_sign);
    	s->next_1 = top;
    	top = s;
    }
    void new_linkstack::push_in(double in_number)
    {
    	struct operate *s;
    	s = new operate;
    	s->member = in_number;
    	s->next = top;
    	top = s;
    }
    double new_linkstack::push_out()
    {
    	struct operate *p;
    	if (top == NULL)throw"下溢";
    	double out_member;
    	out_member = top->member; p = top;
    	top = top->next;
    	delete p;
    	return out_member;
    }
    void new_linkstack::print_result()
    {
    	cout << top->member << endl;
    }
    int main()
    {
    	int count = 0; double m;
    	string a, b;
    	cin >> a;
    	linkstack one;
    	for (auto c = a.begin(); c != a.end(); c++) {
    		if (isdigit(*c)) {
    			b.push_back(*c);  continue;
    		}
    		else {
    			if (*c != ')'&&count == 0) {
    				one.push_in(*c);
    				count++;
    				continue;
    			}
    			if (*c == ')') {
    				while (one.print_top() != '(') {
    					b.push_back(one.print_top());
    					one.push_out(); count--;
    				}
    				one.push_out(); count--;
    				continue;
    			}
    			if (compare(*c) <= one.print_level()) {
    				b.push_back(one.print_top());
    				one.push_out();
    				one.push_in(*c);
    				continue;
    			}
    			if (compare(*c) > one.print_level()) {
    				one.push_in(*c); count++;
    				continue;
    			}
    		}
    	}
    	if (count) {
    		b.push_back(one.print_top());
    		one.push_out();
    	}
    	double x, y, result, new_b;
    	string new_a(b);
    	new_linkstack two;
    	for (auto c = new_a.begin(); c != new_a.end(); c++) {
    		if (isdigit(*c)) {
    			stringstream sstream;
    			sstream << *c;
    			sstream >> new_b;
    			two.push_in(new_b);
    			sstream.clear();
    		}
    		else {
    			x = two.push_out();
    			y = two.push_out();
    			switch (*c)
    			{
    			case '+':
    				result = x + y; two.push_in(result); continue;
    			case '-':
    				result = y - x; two.push_in(result); continue;
    			case '*':
    				result = x * y; two.push_in(result); continue;
    			case '/':
    				result = y / x; two.push_in(result); continue;
    			}
    		}
    	}
    	two.print_result();
    	system("pause");
    	return 0;
    }

    这也算是个人狭义上的第一次模块化的编程吧。。。。。。

    展开全文
  • 数据结构C++版,将中缀表达式变换为后缀并用后缀表达式求值,支持运算符包括+,-,*,/,^,(),支持小数,负数,多位数运算
  • 数据结构课程实验,实现了终端输入输出的中缀表达式求值后缀表达式求值,中缀表达式转化后缀表达式,以及文件流的中缀表达式求值后缀表达式求值,中缀表达式转化后缀表达式,可操作整数,小数,浮点数,实现运算...
  • 后缀表达式求值 首先需要将输入的中缀表达式转换成后缀表达式后缀表达式中,操作符在后 例如:1+2*(5-3)+4 后缀表达式:1253-*+4+ 1、中缀表达式转换成后缀表达式方法: 首先,需要定义一个操作符栈并且知道各...

    中缀表达式转后缀表达式求值

    首先需要将输入的中缀表达式转换成后缀表达式
    后缀表达式中,操作符在后
    例如:1+2*(5-3)+4
    后缀表达式:1253-*+4+

    1、中缀表达式转换成后缀表达式方法:

    首先,需要定义一个操作符栈并且知道各运算符优先级,然后从左往右一次扫描字符(字符前后加#号),遇到数字直接输出,遇到操作符比较优先级。
    栈顶优先级低,入栈;
    栈顶优先级高,出栈并且输出;
    优先级相等(即左右括号),出栈(不输出);
    当扫描的字符为#并且栈顶字符为#时,此时输出的字符序列即为后缀表达式

    2、后缀表达式求值过程

    转换成后缀表达式后,即可利用后缀表达式进行求值,后缀表达式求值时,只需定义一个操作数栈,当从左往右扫描字符串时,扫描到数字时进栈,扫描到字符从栈中出两个数字,然后与扫描到的字符之间进行运算, ***<运算时注意:先出栈的做运算符的后操作数,后出栈的做前操作数>***当全部扫描完之后,栈顶的数字即为求值结果

    3、代码实现

    #include <iostream>
    #include <string>
    using namespace std;
    
    string s;  //中缀表达式字符串
    string s1="\0"; //后缀表达式字符串
    char OPTR[100]; //操作符栈
    char OPND[100]; //操作数栈
    int topN=-1,topT=-1;
    
    //栈的基本操作
    void push(char *OPTR,char ch){
            OPTR[++topT]=ch;
    }
    void push(int *OPND,int val){
            OPND[++topN]=val;
    }
    char pop(char *OPTR){
            return OPTR[topT--];
    }
    int pop(int *OPND){
            return OPND[topN--];
    }
    int getTop(int *OPND){
        return OPND[topN];
    }
    char getTop(char *OPTR){
        return OPTR[topT];
    }
    
    //定义一个二位字符数组存放优先级表
    char arr[7][7]= {'>','>','<','<','<','>','>',
                     '>','>','<','<','<','>','>',
                     '>','>','>','>','<','>','>',
                     '>','>','>','>','<','>','>',
                     '<','<','<','<','<','=','\0',
                     '>','>','>','>','\0','>','>',
                     '<','<','<','<','<','\0','='
                    };
    //定义字符表
    int opCH(char ch){
        int i;
            switch(ch){
        case '+':{
            i=0;
            break;
        }
        case '-':{
            i=1;
            break;
        }
        case '*':{
            i=2;
            break;
        }
        case '/':{
            i=3;
            break;
        }
        case '(':{
            i=4;
            break;
        }
        case ')':{
            i=5;
            break;
        }
        case '#':{
            i=6;
            break;
        }
     }
     return i;
    }
    //比较运算符的优先级
    char percede(char ch1,char ch2){
        int i,j;
        i=opCH(ch1);
        j=opCH(ch2);
        return arr[i][j];
    }
    
    int operate(int a,char theta,int b){
        switch(theta){
        case '+':{
                return a+b;
        }
        case '-':{
                return a-b;
        }
        case '*':{
                return a*b;
        }
        case '/':{
                return a/b;
        }
     }
     return 0;
    
    }
    void suffix(string s){
        for(int i=0;s[i]!='#'||getTop(OPTR)!='#';i++){
            if(s[i]>48&&s[i]<58){
                s1+=s[i];  //如果是数字的话放入新字符串
            }else if(s[i]=='*'||s[i]=='/'||s[i]=='+'||s[i]=='-'||
                     s[i]=='('||s[i]==')'||s[i]=='#'){
                switch(percede(getTop(OPTR),s[i])){
            case '>':{
                    s1+=pop(OPTR);//栈顶优先级高的话放入新字符串
                    i--;
                    break;
            }
            case '<':{
                    push(OPTR,s[i]);
                    break;
            }
            case '=':{
                    if(s[i]==')'){
                        pop(OPTR);
                    }
            }
          }
        }
     }
    }
    
    int calculation(string s1){
        int a,b,c;
        char theta;
        for(int i=0;s1[i]!='\0';i++){
            if(s1[i]>48&&s1[i]<58){
                c=s1[i]-48;
                push(OPND,c);//扫描到操作数压栈
            }else if(s1[i]=='*'||s1[i]=='/'||s1[i]=='+'||s1[i]=='-'){
                b=pop(OPND);//扫描到操作符就 从栈中弹出两个操作数进行运算
                a=pop(OPND);
                theta=s1[i];
                push(OPND,operate(a,theta,b));
    
            }
        }
        return getTop(OPND);
    }
    int main(){
    push(OPTR,'#');
    cout<<"请输入中缀表达式,以#符号结束:";
    cin>>s;
    suffix(s);
     cout<<"后缀表达式:";
      cout<<s1<<endl;
      cout<<"表达式结果:";
      cout<<calculation(s1)<<endl;
        return 0;
    }
    

    代码实现与中缀表达式求值类似

    中缀表达式求值:

    https://blog.csdn.net/weixin_51799151/article/details/120643674

    展开全文
  • #include #include #include #define MaxSize 99 char calc[MaxSize]; int i; struct { int data[MaxSize]; int top; } Num;... } } printf("后缀表达式为: %d\n",Num.data[Num.top]); return 0; }

    #include<stdio.h>
    #include<stdlib.h>
    #include<math.h>
    #define MaxSize 99
    char calc[MaxSize];
    int i;
    struct {
        int data[MaxSize];
        int top;
    } Num;
    void NumPush(int  a) {
        if(Num.top<MaxSize-1) {
            Num.data[++Num.top]=a;
        } else {
            printf("Num栈满\n");

        }
    }
    void NumPop() {
        if(Num.top>=0) {

                switch(calc[i]) {
                    case '+':
                            Num.data[Num.top-1]=Num.data[Num.top-1]+Num.data[Num.top];
                        break;
                    case '-':
                            Num.data[Num.top-1]=Num.data[Num.top-1]-Num.data[Num.top];
                        break;
                    case '*':
                            Num.data[Num.top-1]=Num.data[Num.top-1]*Num.data[Num.top];
                        break;
                    case '/':
                            Num.data[Num.top-1]=Num.data[Num.top-1]/Num.data[Num.top];
                        break;

                }
                Num.top--;

        } else {
            printf("Num栈空\n");

        }
    }
    int main(){
        gets(calc);

        int k;int  sum=0;
        Num.top=-1;
        for(k=0;calc[k]!='\0';k++)
        for(i=0;i<=k;){

            if(calc[i]>='0'&&calc[i]<='9'){
                sum=calc[i]-'0';i++;
                while(calc[i]>='0'&&calc[i]<='9'){
                        sum=sum*10+calc[i++]-'0';

                }
                NumPush(sum);

            }
            else if(calc[i]=='-'&&calc[i+1]>='0'&&calc[i]<='9'){
                     sum=calc[i]-'0';i++;
                while(calc[i]>='0'&&calc[i]<='9'){
                        sum=sum*10+calc[i++]-'0';

                }
                NumPush(-sum);


            }

            else if(calc[i]=='+'||calc[i]=='-'||calc[i]=='*'||calc[i]=='/'){
                NumPop();
                i++;
            } else
            {
                i++;

            }
        }
        printf("后缀表达式的值为:  %d\n",Num.data[Num.top]);
        return 0;
    }
     

    展开全文
  • 题目: 利用栈编写表达式求值程序:输入含有“ + ...由于表达式的运算符号为字符类型,但依然能够以ASCII码形式储存在栈中,故栈元素可以不用定义为字符类型,而定义为整型类型数据即可,方便从后缀表达式中将字符类型.

    题目:
    利用栈编写表达式求值程序:输入含有“ + ”、“ - ”、“ * ”、“ / ”四则运算的表达式,其中负数要用(0 - 正数)表示,并以 = 结束。要求输出表达式的值。

    输入格式
    第一行:一个算术表达式
    输出格式
    第一行:算术表达式的值
    输入样例
    3 * (9 - 7) =
    输出样例
    6

    一、解题思路:

    ①. 注意栈元素为整型类型。由于表达式的运算符号为字符类型,但依然能够以ASCII码形式储存在栈中,故栈元素可以不用定义为字符类型,而定义为整型类型数据即可,方便从后缀表达式中将字符类型转变为整型类型进行处理,保持了栈元素类型的一致性,方便处理
    ②. 本代码借用 ‘#’ 分隔数字,故本程序可以处理多位数运算的表达式

    步骤一:

    中缀表达式:
    3 - 10 * ( 9 - 12 ) =
    

    从键盘中输入中缀表达式字符串,创建符号栈operate处理中缀表达式,将其转变为后缀表达式储存在字符串suffix[]中

    步骤二:

    后缀表达式:
    3#10#9#12#-*-
    

    处理后缀表达式字符串:创建数字栈number,遍历后缀表达式,如果是数字,则入栈; 如果是运算符,则出栈两个整型数字a,b,分别作为操作数和被操作数进行运算,把运算结果入栈; 后缀表达式遍历结束后,栈中仅存一个元素即为后缀表达式的运算结果

    运算结果:

    33
    

    二、代码模块:

    ①、栈的建立基本函数:

    #include<malloc.h> 
    #include<stdio.h> 
    #include<string.h>
    
    #define OK 1
    #define ERROR 0
    #define STACK_INIT_SIZE 100 // 存储空间初始分配量
    #define STACKINCREMENT 10 // 存储空间分配增量
    
    typedef int SElemType; // 定义栈元素类型
    typedef int Status; // Status是函数的类型,其值是函数结果状态代码,如OK等
    
    struct SqStack
    {
    	SElemType* base; // 在栈构造之前和销毁之后,base的值为NULL
    	SElemType* top; // 栈顶指针
    	int stacksize; // 当前已分配的存储空间,以元素为单位
    }; // 顺序栈
    
    Status InitStack(SqStack& S)
    {
    	// 构造一个空栈S,该栈预定义大小为STACK_INIT_SIZE
    	S.base = (SElemType*)malloc(STACK_INIT_SIZE * sizeof(SElemType));
    	if (!S.base) return ERROR;
    	S.top = S.base;
    	S.stacksize = STACK_INIT_SIZE;
    	return OK;
    }
    
    Status Push(SqStack& S, SElemType e)
    {
    	// 在栈S中插入元素e为新的栈顶元素
    	if (S.top - S.base >= S.stacksize)
    	{
    		S.base = (SElemType*)realloc(S.base, (S.stacksize + STACKINCREMENT) * sizeof(SElemType));
    		if (!S.base) return ERROR;
    		S.top = S.base + S.stacksize;
    		S.stacksize += STACKINCREMENT;
    	}
    	*S.top++ = e;
    	return OK;
    }
    
    Status Pop(SqStack& S, SElemType& e)
    {
    	// 若栈不空,则删除S的栈顶元素,用e返回其值,并返回OK;否则返回ERROR
    	if (S.top == S.base) return ERROR;
    	e = *--S.top;
    	return OK;
    }
    
    Status GetTop(SqStack S, SElemType& e)
    {
    	// 若栈不空,则用e返回S的栈顶元素,并返回OK;否则返回ERROR
    	if (S.top == S.base) return ERROR;
    	e = *(S.top - 1);
    	return OK;
    }
    
    int StackLength(SqStack S)
    {
    	// 返回栈S的元素个数
    	int i;
    	i = S.top - S.base;
    	return i;
    }
    
    Status StackTraverse(SqStack S)
    {
    	// 从栈顶到栈底依次输出栈中的每个元素
    	SElemType* p = (SElemType*)malloc(sizeof(SElemType));
    	p = S.top;
    	if (S.top == S.base)printf("The Stack is Empty!");
    	else
    	{
    		printf("The Stack is: ");
    		p--;
    		while (p >= S.base)
    		{
    			printf("%d ", *p);
    			p--;
    		}
    	}
    	printf("\n");
    	return OK;
    }
    

    ②、结合主函数中的if分支对中缀表达式的字符判断运算符的优先级:

    //比较栈顶符号和当前符号的优先级,如果栈顶符号优先级较高,则一直出栈,最后把当前符号入栈;否则,当前符号入栈
    int ComparePriority(SElemType stackTop, SElemType cur)
    {
    	switch (stackTop)
    	{
    	case '(':
    		return 1;
    		break;
    	case '+':
    	case '-':
    		if (cur == '*' || cur == '/')
    			return 1;
    		break;
    	default:
    		break;
    	}
    	return 0;
    }
    
    

    ③、操作数与被操作数的运算:

    //运算函数
    int Calculate(SElemType ch, int a, int b)
    {
    	int result = 0;
    
    	switch (ch)
    	{
    	case '+':
    		result = b + a;
    		break;
    	case '-':
    		result = b - a;
    		break;
    	case '*':
    		result = b * a;
    		break;
    	case '/':
    		result = b / a;
    		break;
    	default:
    		break;
    	}
    	return result;
    }
    

    ④、主函数(包括中缀表达式转化为后缀表达式和后缀表达式的求值):

    
    int main()
    {
    	char s[1000];
    	gets_s(s,1000);
    	char suffix[1000];
    	int index_su = 0;
    
    	/*中缀表达式转化为后缀表达式*/
    	
    	//初始化符号栈,整型元素栈
    	SqStack operate;
    	InitStack(operate);
    
    	int i;
    	int e;
    	for (i = 0; i < strlen(s); i++)
    	{
    		if (s[i] >= '0' && s[i] <= '9')//是数字,保存到后缀表达式中
    		{
    			suffix[index_su++] = s[i];
    			if (s[i + 1] < '0' || s[i + 1] > '9')
    			{
    				suffix[index_su++] = '#';
    			}
    		}
    		else if (s[i] == ' ' || s[i] == '=')//是空格或等号,忽略
    		{
    			continue;
    		}
    		else//是运算符号,需要入栈出栈判断处理
    		{
    			SElemType top;
    			GetTop(operate, top);
    			if (StackLength(operate) == 0 || s[i] == '(')//如果栈为空,或者当前符号为左括号,则入栈
    			{
    				Push(operate, s[i]);
    			}
    			else if (s[i] == ')')//如果当前符号是右括号,则一直出栈
    			{
    				do
    				{
    					Pop(operate, e);
    					if (e != '(')
    					{
    						suffix[index_su++] = e;
    					}
    				} while (e != '(');
    			}
    			else if (ComparePriority(top, s[i]) == 1)//当前符号优先级较高
    			{
    				Push(operate, s[i]);
    			}
    			else if (ComparePriority(top, s[i]) == 0)//栈顶符号优先级较高
    			{
    				do
    				{
    					Pop(operate, e);
    					suffix[index_su++] = e;
    					GetTop(operate, top);//重新获取栈顶符号
    				} while (ComparePriority(top, s[i]) == 0 && StackLength(operate) != 0);//当栈中还有符号并且栈顶符号优先级较高时,出栈
    				Push(operate, s[i]);//当前符号入栈
    			}
    		}
    	}
    
    	//把栈中元素全部出栈,保存到后缀表达式中
    	do
    	{
    		Pop(operate, e);
    		suffix[index_su++] = e;
    	} while (operate.top > operate.base);
    
    	suffix[index_su] = '\0';//结束后缀表达式
    	puts(suffix);
    
    
    	/*后缀表达式求值*/
    
    	//初始化数栈
    	SqStack number;
    	InitStack(number);
    
    	int num = 0;
    	for (i = 0; i < strlen(suffix); i++)
    	{
    		if (suffix[i] >= '0' && suffix[i] <= '9')
    		{
    			while (suffix[i] != '#')
    			{
    				num = num * 10 + (suffix[i++] - '0');
    			}
    			Push(number, num);
    			//printf("num = %d\n", num);
    			num = 0;
    		}
    		else
    		{
    			int a, b;
    			Pop(number, a);
    			Pop(number, b);
    			int result = Calculate(suffix[i], a, b);
    			//printf("a = %d, b = %d, result = %d\n", a, b, result);
    			Push(number, result);
    		}
    	}
    	int result;
    	Pop(number, result);
    	printf("%d\n", result);
    
    	return 0;
    }
    

    有任何问题可以留言交流,我一定及时回复

    展开全文
  • NULL 博文链接:https://128kj.iteye.com/blog/1623312
  • 这是数据结构里的一个后缀表达式求值问题,小数和十位上的数计算都能求值 主要用到栈
  • 该程序实现了运算表达式转换为中缀表达式、中缀表达式转换为后缀表达式后缀表达式求值。该程序已实现加减乘除括号运算符及余、幂指数的求解
  • ​ 上次已经完成了由中缀表达式转后缀表达式的算法,而后缀表达式的优点就是可以从左至右直接读取,没有算数优先级的考量,所以直接进行运算即可。 ​ 该算法需要使用一个栈用来保存操作数,在读取到数字的时候,将...
  • 中缀表达式的求值 中缀表达式的求值可以通过将中缀表达式先转为后缀表达式,再对后缀表达式求值实现。 因此,我们介绍中缀表达式转后缀表达式与对后缀表达式求值两个步骤,只要将这两个步骤合并就是对中缀表达式求值...
  • 表达式求值(中缀转后缀及后缀表达式求值

    万次阅读 多人点赞 2017-04-21 13:05:59
    中缀表达式转后缀表达式:中缀表达式转后缀表达式遵循以下原则: 1.遇到操作数,直接输出; 2.栈为空时,遇到运算符,入栈; 3.遇到左括号,将其入栈; 4.遇到右括号,执行出栈操作,并将出栈的元素输出,...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 101,780
精华内容 40,712
关键字:

后缀表达式求值