数学表达式求值

成绩 10 开启时间 2017年10月18日 星期三 17:40
折扣 0.8 折扣时间 2017年11月8日 星期三 23:55
允许迟交 关闭时间 2018年01月8日 星期一 23:55

问题描述

  带有变量的中缀表达式是常见的数学表达式。如果规定变量由长度不超过 8 个小写字母组成;end为保留字,表示程序段结束;用?表示输出指定变量的值,则可以设计出比较复杂的表达式(即一个可顺序执行语句序列)。例如,如果有如下语句段:

abc=10
def=8
c=abc+def
abc=abc+5-c*2
? c
? abc
end

则输出为:

c=18
abc=-21

注意:为了简化编程实现,运算符只有+,-,*,/ ,%和^(指数运算),可以处理圆括号(),并假定输入的算术表达式正确。

要求:使用栈结构实现。

输入:表达式序列

输出:全部指定变量的值

表达式中的全部计算结果均为整数。如果在计算过程中出现除数为0的情况,则输出:Divide 0.

特殊情况说明:
在表达式中,如果操作数出现负数(例如-8),则要特别注意。例如:
10加-8表示为:10+-8。
10减-8表示为:10--8。

  测试输入 期待的输出 时间限制 内存限制 额外进程
测试用例 1 以文本方式显示
  1. abc=10↵
  2. def=8↵
  3. c=abc+def↵
  4. abc=abc+5-c*2↵
  5. ? c↵
  6. ? abc↵
  7. end↵
以文本方式显示
  1. c=18↵
  2. abc=-21↵
1秒 64M 0
测试用例 2 以文本方式显示
  1. a=12↵
  2. b=5↵
  3. c=a/b↵
  4. d=(a+1)%(b+1)↵
  5. e=a^2↵
  6. f=-12+a↵
  7. g=(a+5)*d-c↵
  8. ? c↵
  9. ? d↵
  10. ? e↵
  11. ? f↵
  12. ? g↵
  13. a=a+10↵
  14. ? a↵
  15. end↵
以文本方式显示
  1. c=2↵
  2. d=1↵
  3. e=144↵
  4. f=0↵
  5. g=15↵
  6. a=22↵
1秒 64M 0
测试用例 3 以文本方式显示
  1. abc=3↵
  2. ab=2^(abc-1)^(5-abc)↵
  3. ? ab↵
  4. end↵
以文本方式显示
  1. ab=16↵
1秒 64M 0
测试用例 4 以文本方式显示
  1. a=2↵
  2. b=a^(a+1)^(10-8)↵
  3. ? b↵
  4. end↵
以文本方式显示
  1. b=512↵
1秒 64M 0
测试用例 5 以文本方式显示
  1. a=10↵
  2. ? a↵
  3. b=-10+10↵
  4. ? b↵
  5. a=-10-10↵
  6. ? a↵
  7. c=a+-10+-10↵
  8. ? c↵
  9. d=-20+-8-8↵
  10. ? d↵
  11. e=a-12*-2↵
  12. ? e↵
  13. f=80--10+2↵
  14. ? f↵
  15. g=-10--10↵
  16. ? g↵
  17. h=-10+-10↵
  18. ? h↵
  19. i=(90)↵
  20. ? i↵
  21. k=(-100)↵
  22. ? k↵
  23. end↵
以文本方式显示
  1. a=10↵
  2. b=0↵
  3. a=-20↵
  4. c=-40↵
  5. d=-36↵
  6. e=4↵
  7. f=92↵
  8. g=0↵
  9. h=-20↵
  10. i=90↵
  11. k=-100↵
1秒 64M 0
测试用例 6 以文本方式显示
  1. abcdefgh=4↵
  2. ten=10↵
  3. a=18-32↵
  4. ? a↵
  5. b=18/abcdefgh↵
  6. ? b↵
  7. c=18%(b-1)↵
  8. ? c↵
  9. d=ten+(ten+ten)*abcdefgh↵
  10. ? d↵
  11. e=ten-2*ten/abcdefgh↵
  12. ? e↵
  13. f=(18-3)*3↵
  14. ? f↵
  15. ten=ten*(ten)↵
  16. ? ten↵
  17. ten=ten/10↵
  18. ten=(ten+2)/(8-ten)↵
  19. ? ten↵
  20. h=(2*3)/(5*2)↵
  21. ? h↵
  22. ten=10↵
  23. x=ten-(80-30)/3*3+abcdefgh↵
  24. y=(((2+8)*2-(2+abcdefgh)/2)*2-8)*2↵
  25. z=(((8+2)*(abcdefgh/2)))↵
  26. ? x↵
  27. ? y↵
  28. ? z↵
  29. end↵
以文本方式显示
  1. a=-14↵
  2. b=4↵
  3. c=0↵
  4. d=90↵
  5. e=5↵
  6. f=45↵
  7. ten=100↵
  8. ten=-6↵
  9. h=0↵
  10. x=-34↵
  11. y=52↵
  12. z=20↵
1秒 64M 0

#include 
#include 
#include 
#include 
#include 
#include 
using namespace std; 
 
map Varible; 
stack Op; 
stack  Opnum; 
string Instruction; 
string tmp; 
 
int GetproiIncoming(char c)    //栈外的优先级
{ 
    switch (c) 
 { 
  case('+') : return 3; 
  case('-') : return 3; 
  case('*') : return 5; 
  case('/') : return 5; 
  case('%') : return 5; 
  case('(') : return 10; 
 case('^') : return 8; 
  } 
} 
 
int GetproInstack(char c)   //栈内的优先级
{ 
   switch (c) 
 { 
  case('+') : return 4; 
  case('-') : return 4; 
  case('*') : return 6; 
  case('/') : return 6; 
  case('%') : return 6; 
  case('(') : return 1; 
  case('^') : return 7; 
  } 
} 
 
int comput(char c, int a, int b) 
{ 
    switch (c) 
 { 
  case('+') : return a+b; 
    case('-') : return a-b; 
    case('*') : return a*b; 
    case('/') : return a/b; 
    case('%') : return a%b; 
    case('^') : return (int)pow(double(a),double(b)); 
  } 
} 
 
int Getvar(string tmp) 
{ 
  int num = 0; 
   for (int i = 0; tmp[i]; i++) 
   { 
      if (tmp[i] >= '0'&&tmp[i] <= '9') 
        { 
          num = num * 10 + tmp[i] - '0'; 
     } 
      else if (tmp[i] >= 'a'&&tmp[i] <= 'z') 
       { 
          string var; 
            int k = i; 
         while (tmp[k] >= 'a'&&tmp[k] <= 'z') 
         { 
              k++; 
           } 
          var = tmp.substr(i, k-i); 
          Opnum.push(Varible[var]); 
          i = k - 1; 
     } 
      else if (!(tmp[i] >= '0'&&tmp[i] <= '9') && !(tmp[i] >= 'a'&&tmp[i] <= 'z')) 
       { 
          if (tmp[i] == '=') continue; 
           if ((tmp[i - 1] >= '0'&&tmp[i - 1] <= '9')) 
          { 
              Opnum.push(num); num = 0; 
          } 
          else if (!(tmp[i - 1] >= '0'&&tmp[i - 1] <= '9') && !(tmp[i - 1] >= 'a'&&tmp[i - 1] <= 'z')&&(tmp[i]=='+'||tmp[i]=='-')) 
           { 
              i++; int k = i; 
                while (tmp[k] && (tmp[k] >= '0'&&tmp[k] <= '9')) 
             { 
                  num = num * 10 + tmp[k] - '0'; k++; 
                } 
              if (tmp[i - 1] == '-') num *= -1;   i = k - 1; continue; 
           } 
          if (Op.empty()||tmp[i]=='(') 
           { 
              Op.push(tmp[i]); continue; 
         } 
          else if (tmp[i] == ')') 
            { 
              char op; 
               while (!Op.empty() && (op = Op.top()) != '(') 
              { 
                  int b = Opnum.top(); Opnum.pop(); 
                  int a = Opnum.top(); Opnum.pop(); 
                  if (b == 0 && op == '/') 
                       continue; 
                  else { Opnum.push(comput(op,a,b)); } 
                   Op.pop(); 
              } 
              Op.pop(); 
            } 
            else 
           { 
              int Incoming = GetproiIncoming(tmp[i]); 
                int Instack; 
               char op; 
               while (!Op.empty()&&(Instack = GetproInstack(Op.top())) > Incoming) 
             { 
                  op = Op.top(); 
                 int b = Opnum.top(); Opnum.pop(); 
                  int a = Opnum.top(); Opnum.pop(); 
                  if (b == 0 && op == '/') 
                       continue; 
                  else { Opnum.push(comput(op, a, b)); } 
                 Op.pop(); 
              } 
              Op.push(tmp[i]); 
           } 
      } 
  } 
  if (tmp[tmp.length()-1] >= '0'&&tmp[tmp.length()-1] <= '9') 
      Opnum.push(num); 
   if (!Op.empty()||!Opnum.empty()) 
   { 
 
     while (!Op.empty()) 
        { 
          char op = Op.top(); 
            int b = Opnum.top(); Opnum.pop(); 
          int a = Opnum.top(); Opnum.pop(); 
          if (b == 0 && op == '/') 
               continue; 
          else { Opnum.push(comput(op, a, b)); } 
         Op.pop(); 
      } 
      return Opnum.top(); 
    } 
  else return num; 
} 
int main() 
{ 
    //freopen("1.txt", "r", stdin); 
    while (getline(cin,Instruction)) 
   { 
      if (Instruction == "end") 
          break; 
     while (!Op.empty()) 
            Op.pop(); 
      while (!Opnum.empty()) 
         Opnum.pop(); 
       if (Instruction[0] == '?') 
     { 
          tmp = Instruction.substr(2); 
           int num = Varible.find(tmp)->second; 
            cout << tmp<< '='<= 'a'&&Instruction[0] <= 'z') 
       { 
          int i = 0; 
         string varble; 
         while (Instruction[i] != '=') 
          { 
              i++; 
           } 
          varble = Instruction.substr(0, i); 
         if (Varible.count(varble) == 0) 
            { 
              Varible[varble] = 0; 
                
           } 
          string tmp = Instruction.substr(i); 
            Varible[varble] = Getvar(tmp); 
     } 
  } 
  return 0; 
} 


你可能感兴趣的:(大二上数据结构练习)