问题描述
令二元函数f(x,y)=ax+by,a和b为整数,求一个表达式S的值。
只有满足以下要求的表达式才是合法的:
1.任意整数x是一个合法的表达式;
2.如果A和B都是合法的表达式,则f(A,B)也是一个合法的表达式。
只有满足以下要求的表达式才是合法的:
1.任意整数x是一个合法的表达式;
2.如果A和B都是合法的表达式,则f(A,B)也是一个合法的表达式。
输入格式
第一行两个数a和b;
第二行一个字符串S表示要求的表达式。
第二行一个字符串S表示要求的表达式。
输出格式
一行一个数表示表达式S的值。
样例输入
1 2
f(1,f(1,-1))
f(1,f(1,-1))
样例输出
-1
数据规模和约定
S的长度不超过50,运算过程中所有变量不会超出int的范围。
思路:对于表达式之类的除了递归搜索 一般会联想到栈的概念
1:如果有f(12, 123)这样的12,123多位数字如何操作。正解应是传递引用的形参表示索引
2:什么时候弹出栈顶元素没有想到,其实可以不用考虑字符f和左括号的。
#include <iostream> #include <cstdio> #include <algorithm> #include <stack> using namespace std; int a, b; // 表达式中的系数 string s; // 输入的字符串 int f(int x, int y) // 返回f表达式计算得到的值 { return a * x + b * y; } int getnum(int &i, bool minus) // 参数i为引用 可以控制原循环i值变化 { // minus 用于判断是否为负数 int num = 0; while (s[i] >= '0' && s[i] <= '9') { num = num * 10 + s[i] - '0'; i ++ ; // 在函数里面进行指针的变化 妙啊~ 之前是想不到这样做的 } if (minus) num = -num; return num; } int main() { cin >> a >> b >> s; stack<int> stk; // stk.push(0); // 压入 0, 若输入空字符串 应弹出0 但实际上没必要 毕竟题目没要求 for (int i = 0; i < s.size(); i ++ ) { if (s[i] == '-') // 如果这一位是负号,下一位一定是数字,i移动到下一位 { i ++ ; stk.push(getnum(i, true)); } else if (s[i] >= '0' && s[i] <= '9') // 如果这一位是数字的话压入数字(必为正数,负数在上一个if那里判断了) { // 这就是通过i值引用的巧妙之处 stk.push(getnum(i, false)); } if (s[i] == ')') // 如果这一位是右括号,意味着有一个f表达式可以计算了 { int y = stk.top(); stk.pop(); int x = stk.top(); stk.pop(); stk.push(f(x, y)); } } cout << stk.top() << endl; return 0; }