中缀表达式计算、后缀表达式计算、中缀转后缀

代码来源 :
bilibili网站 :https://www.bilibili.com/video/av91996256?from=search&seid=17449723308302029804

注意:中缀表达式 转 后缀表达式,函数 有误。

中缀表达式 计算过程 :
在这里插入图片描述

后缀表达式 计算过程 :
在这里插入图片描述

中缀表达式 转 后缀表达式 :
在这里插入图片描述

/* 前缀:prefix
** 中缀:Infix
** 后缀:Suffix
exit为C++的退出函数,声明于stdlib.h中,对于C++其标准的头文件为cstdlib,
声明为 void exit(int value);
exit的功能为,退出当前运行的程序,并将参数value返回给主调进程。
在main中return v;的效果 与exit(v);相同。
exit(1)和exit(-1)是分别返回1和-1到主调程序。
exit(0): 返回0,表示程序正常退出,非0表示非正常退出。
exit(1):表示异常退出。
*/

#include <stdio.h>
#include <stdlib.h>
// #include <cstring>
#include <string.h>

enum boolean
{
    FALSE,
    TRUE
};

typedef enum boolean Bool; //枚举方式进行重定义
typedef int ElementType;

struct stack
{
    ElementType *element;
    int MaxSize; //大小
    int top;     //线性表:长度; 栈:栈顶指针
};

typedef struct stack Stack;

//需要的函数
void InitStack(Stack *S, int sz);   //初始化函数
void FreeStack(Stack *S);           //释放栈空间(即: 空间无)
Bool Push(Stack *S, ElementType X); //压栈
ElementType Pop(Stack *S);          //弹栈(栈顶弹出)
ElementType GetTop(Stack *S);       // 获取栈顶元素
void MakeStackEmpty(Stack *S);      //置空(无元素,空间依然存在)
Bool IsStackEmpty(Stack *S);        //栈是否为空
Bool IsStackFull(Stack *S);         //栈是否为满

void EvaluteMidPostfix();  //中缀表达式求值
void EvaluteBackPostfix(); //后缀表达式求值
void MidToBack();          //中缀转后缀

int main()
{
    //printf("%d\n", (int)('9' - 48));

    //EvaluteMidPostfix();
    EvaluteBackPostfix();
    //MidToBack();
    return 0;
}

//实现各个功能函数

void InitStack(Stack *S, int sz) //初始化栈(栈为空)
{
    S->MaxSize = sz;
    S->top = -1; //指向-1; 一个元素:指向0
    S->element = (ElementType *)malloc(sizeof(ElementType) * S->MaxSize);
}

void FreeStack(Stack *S) //释放栈空间(即: 空间无)
{
    free(S->element); //释放元素
}

Bool IsStackFull(Stack *S) //栈是否为满
{
    // return S->top == S->MaxSize-1;
    if (S->top == S->MaxSize - 1)
        return TRUE;
    return FALSE;
}

Bool IsStackEmpty(Stack *S) //栈是否为空
{
    //return S->top == -1;
    if (S->top == -1)
        return TRUE;
    return FALSE;
}

Bool Push(Stack *S, ElementType x) //压栈
{
    //先判断 栈满?
    if (IsStackFull(S))
        return FALSE;
    else
    {
        //指针指向新的栈顶
        S->element[++S->top] = x; //top先加一
        return TRUE;
    }
}

ElementType Pop(Stack *S) //弹栈(栈顶弹出)
{
    if (IsStackEmpty(S))
    {
        //return FALSE;
        exit(1); //表示异常退出
    }
    else
    {
        //先弹出元素,指针下移
        return S->element[S->top--];
    }
}

ElementType GetTop(Stack *S) // 获取栈顶元素
{
    if (IsStackEmpty(S))
    {
        //return FALSE;
        exit(1); //表示异常退出
    }
    else
    {
        //先弹出元素,指针下移
        return S->element[S->top];
    }
}

void MakeStackEmpty(Stack *S) //置空(无元素,空间依然存在)
{
    S->top = -1;
}

//从操作数栈取两个操作数;从操作符栈取一个操作符
//用操作符对操作数进行运算。将计算结果压入操作数栈。
void compute(Stack *Sptr, Stack *Spnd) //定义计算过程
{
    int k;
    switch (Pop(Sptr))
    {
    case '+':
        k = Pop(Spnd) + Pop(Spnd);
        break;
    case '-':
        k = Pop(Spnd);
        k = Pop(Spnd) - k;
        break;
    case '*':
        k = Pop(Spnd) * Pop(Spnd);
        break;
    case '/':
        k = Pop(Spnd);
        k = Pop(Spnd) / k;
        break;
    }
    Push(Spnd, k); //将计算结果压入操作数栈。
}

void EvaluteMidPostfix() //中缀表达式计算求值
{
    char buf[80];
    printf("Please input Infix : \n");
    scanf("%s", buf);

    //strcpy_s(buf, 80, "8-(3+5-4/2)*2/3");

    Stack *Spnd = (Stack *)malloc(sizeof(Stack));
    Stack *Sptr = (Stack *)malloc(sizeof(Stack));

    InitStack(Spnd, 80);
    InitStack(Sptr, 80);

    int i = 0;
    while (buf[i] != '\0')
    {
        //操作数类型
        if (buf[i] >= '0' && buf[i] <= '9')
            Push(Spnd, (int)(buf[i] - 48)); //printf("%d",(int)('9'-48));
        //操作符类型
        //优先级最高(若无括号&&之后也是*或/,从左到右计算)
        else if (buf[i] == '*' || buf[i] == '/') 
        {
            // if(Sptr->top == -1 || GetTop(Sptr)=='(')//操作符直接入栈的条件
            //     Push(Sptr,buf[i]);
            if (GetTop(Sptr) == '*' || GetTop(Sptr) == '/')
            {
                compute(Sptr, Spnd);
            }
            Push(Sptr, buf[i]);
        }
        else if (buf[i] == '+' || buf[i] == '-')
        {
            while (Sptr->top != -1 && GetTop(Sptr) != '(') //判断语句不可交换位置。
            {
                compute(Sptr, Spnd);
            }
            Push(Sptr, buf[i]);
        }
        else if (buf[i] == ')')
        {
            while (GetTop(Sptr) != '(')
            {
                compute(Sptr, Spnd);
            }
            Pop(Sptr);
        }
        else if (buf[i] == '(')
        {
            Push(Sptr, buf[i]);
        }
        i++;
    }
    while (Sptr->top != -1) //结束条件: 操作符栈为空
        compute(Sptr, Spnd);
    printf("%d", Pop(Spnd));
}

void EvaluteBackPostfix() //后缀表达式计算求值
{
    char buf[80];
    printf("Please input Suffix : \n");
    scanf("%s", buf);
    Stack *Spnd = (Stack *)malloc(sizeof(Stack));
    InitStack(Spnd, 80);

    int i = 0, k;
    while (buf[i] != '\0')
    {
        switch (buf[i])
        {
        case '+':
            k = Pop(Spnd) + Pop(Spnd);
            Push(Spnd, k);
            break;
        case '-':
            k = Pop(Spnd);
            k = Pop(Spnd) - k;
            Push(Spnd, k);
            break;
        case '*':
            k = Pop(Spnd) * Pop(Spnd);
            Push(Spnd, k);
            break;
        case '/':
            k = Pop(Spnd);
            k = Pop(Spnd) / k;
            Push(Spnd, k);
            break;
        default:
            Push(Spnd, (int)(buf[i] - 48));
        }
        i++;
    }
    printf("%d", Pop(Spnd));
}

void MidToBack() //中缀转后缀
{
    char buf[80];
    printf("Infix to suffix : \n");
    scanf("%s", buf); // 读入中缀表达式

    //strcpy_s(buf, 80, "8-(3+5-4/2)*2/3");

    Stack *Sptr = (Stack *)malloc(sizeof(Stack));

    InitStack(Sptr, 80);

    int i = 0;
    while (buf[i] != '\0')
    {
        //操作数类型
        if (buf[i] >= '0' && buf[i] <= '9')
            printf("%c", buf[i]);
        //操作符类型
        else if (buf[i] == '*' || buf[i] == '/')
        {
            if (IsStackEmpty(Sptr))
            {
                Push(Sptr, buf[i]); //栈空,往里放东西
            }
            else if (GetTop(Sptr) == '*' || GetTop(Sptr) == '/')
            {
                printf("%c", Pop(Sptr));
                Push(Sptr, buf[i]);
            }
            else
            {
                Push(Sptr, buf[i]);
            }
        }
        else if (buf[i] == '+' || buf[i] == '-')
        {
            if (IsStackEmpty(Sptr))
            {
                Push(Sptr, buf[i]); //栈空,往里放东西
            }
        }
        else if (buf[i] == ')')
        {
            while (GetTop(Sptr) != '(')
            {
                printf("%c", Pop(Sptr));
            }
            Pop(Sptr);
        }
        else if (buf[i] == '(')
        {
            Push(Sptr, buf[i]);
        }
        i++;
    }
    while (Sptr->top != -1) //结束条件: 操作符栈为空
        printf("%c", Pop(Sptr));
}

// 中缀:8-(3+5-4/2)*2/3 : 4
// 中缀:7+2*3/(2-3) : 1
// 后缀:234*+82/- : 10
// 中后:8-(3+5-4/2)*2/3 : 83542/-+2*3/- : 4
// 中后:2*(3+4)-8/2 : 234+*82/-

运行截图:
在这里插入图片描述

发布了28 篇原创文章 · 获赞 54 · 访问量 1万+

猜你喜欢

转载自blog.csdn.net/weixin_44949135/article/details/105003410