zoukankan      html  css  js  c++  java
  • 【1】简单计算器(栈)

    第一篇博客嘎嘎

    问题描述:读入一个只包含 +, -, *, / 的非负整数计算表达式,计算该表达式的值。

    思路:建立两个栈,分别是:运算符栈,用于中缀表达式转化为后缀表达式;操作数栈,用于后缀表达式的计算

    #include <iostream>
    #include <cstdio>
    #include <vector>
    #include <stack>
    #include <cstring>
    #include <stdlib.h>
    #include <stdio.h>
    using namespace std;
     
    struct stNode
    {
      int nType; //元素的类型,0操作数,1操作符
      double nNum; //操作数
      char cOp; //操作符
    };
     
    stack<char> sop; //运算符栈,用于中缀表达式转换成后缀表达式
    stack<double> sNum; //操作数栈,用于后缀表达式的计算
    char cExp[1024]; //读入的字符表达式
    vector<stNode> SuffixExp; //后缀表达式
     
    inline float GetNum(const char* p, int& k)
    {
      int n = atoi(p);
      k = 0;
      while (isdigit(p[k]))
        ++k;
      return n;
    }
     
    inline int get_ip(char c) //获取栈内优先级
    {
      switch (c)
      {
      case '#':
        return 0;
      case '+':
      case '-':
        return 3;
      case '*':
      case '/':
        return 5;
      }
      return 99;
    }
     
    inline int get_op(char c) //获取栈外优先级
    {
      switch (c)
      {
      case '#':
        return 0;
      case '+':
      case '-':
        return 2;
      case '*':
      case '/':
        return 4;
      }
      return 99;
    }
     
    int main(void)
    {
      memset(cExp, 0, sizeof(cExp)); //初始化栈
      while(cin.getline(cExp, 1024))
      {
      //读入字符表达式
      if(strlen(cExp)==1 && cExp[0]=='0') break;
      strcat(cExp, "#");
      while (!sop.empty()) //清空操作符栈
        sop.pop();
      sop.push('#'); //放入界定符
     
      //将中缀表达式转化成后缀表达式
      char *p = cExp;
      while (p[0] != '')
      {
        if (p[0] == ' ') //空格跳过
        {
          ++p;
          continue;
        }
        if (isdigit(p[0]))
        {
          //数字输出到后缀表达式
          int k;
          double n = GetNum(p, k);
          stNode stTemp;
          stTemp.nType = 0;
          stTemp.nNum = n;
          stTemp.cOp = 0;
          SuffixExp.push_back(stTemp);
          p += k;
        }
        else
        {
          char ch1 = p[0];
          char ch2 = sop.top();
          if (get_op(ch1) > get_ip(ch2))
          {
            sop.push(ch1);
            ++p;
          }
          else if (get_op(ch1) < get_ip(ch2))
          {
              //输出到后缀表达式
            stNode stTemp;
            stTemp.nType = 1;
            stTemp.nNum = 0;
            stTemp.cOp = ch2;
            SuffixExp.push_back(stTemp);
            sop.pop();
          }
          else
          {
            sop.pop();
            ++p;
          }
        }
      }
     
      //后缀表达式的计算
      while (!sNum.empty()) //清空操作数栈
        sNum.pop();
      for (int i = 0; i < (int)SuffixExp.size(); ++i)
      {
        if (SuffixExp[i].nType == 0)
          sNum.push(SuffixExp[i].nNum);
        else
        {
          double y = sNum.top();
          sNum.pop();
          double x = sNum.top();
          sNum.pop();
          switch (SuffixExp[i].cOp)
          {
          case '+':
            x += y;
            break;
          case '-':
            x -= y;
            break;
          case '*':
            x *= y;
            break;
          case '/':
            x /= y;
            break;
          }
          sNum.push(x);
        }
      }
      printf("%.2f
    ", sNum.top()); //输出结果
      return 0;
      }
    }

     知识点:atoi()、memset()【https://blog.csdn.net/qq_27522735/article/details/53374765】、printf("%.2f ", x)【保留两位小数】

  • 相关阅读:
    CSS 选择器
    CSS 用法和特性
    Objective-C 事件响应链
    苹果签名机制
    欧几里得算法
    扩展欧几里得算法
    RSA算法
    动态库加载和代码签名
    __attribute__
    信息熵
  • 原文地址:https://www.cnblogs.com/hl220284/p/10485758.html
Copyright © 2011-2022 走看看