#include<bits/stdc++.h>
using namespace std;
const int MOD = 1e9 + 7;

string remove(string s)
{
    string res;
    for(char c : s){
        if(c != ' ') res += c;
    }
    return res;
}

long long qmi(long long a, long long p)
{
    long long res = 1;
    while(p)
    {
        if(p & 1) res = res * a % MOD;

        a = a * a % MOD;
        p >>= 1;
    }

    return res;
}

vector<string> torp(string expr, map<char, int> prec)
{
    vector<string> output;
    stack<char> ops;
    string num;

    for(int i = 0; i < expr.size(); i++)
    {
        char c = expr[i];
        if(isdigit(c)) num += c;
        else {
            if(!num.empty()) {
                output.push_back(num);
                num.clear();
            }

            if(c == 'a') output.push_back("a");
            else if(c == '(') ops.push(c);
            else if(c == ')') 
            {
                while(!ops.empty() && ops.top() != '(') {
                    output.push_back(string(1, ops.top()));
                    ops.pop();
                }
                if(!ops.empty() && ops.top() == '(') ops.pop();
            }
            else
            {
                //弹出优先级比当前运算符高的
                while(!ops.empty() && ops.top() != '(' && prec.at(ops.top()) >= prec.at(c))
                {
                    output.push_back(string(1, ops.top()));
                    ops.pop();
                }
                ops.push(c);
            }
        }

    }
    if(!num.empty()) output.push_back(num);
    while(!ops.empty())
    {
        output.push_back(string(1, ops.top()));
        ops.pop();
    }
    return output;
}  

//计算后缀表达式
int eval(vector<string> rp, int x)
{
    stack<int> st; //操作数栈

    for(string s : rp)
    {
        if(s == "a") {
            st.push(x); //a替换成x
        }
        else if(s == "+" || s == "-" || s == "*" || s == "^")
        {
            int r = st.top(); st.pop();
            int l = st.top(); st.pop();

            if(s == "+") st.push((l + r) % MOD);
            else if(s == "-") st.push((l - r + MOD) % MOD);
            else if(s == "*") st.push((1ll*l*r) % MOD);
            else if(s == "^") st.push(qmi(l, r));
          
        }  else st.push(atoi(s.c_str()));
    }
    return st.top();
}

int main()
{
    srand(time(0)); //初始化随机数种子

    map<char, int> prec = {
        {'+', 1}, {'-', 1}, {'*', 2}, {'^', 3}
    }; //运算符优先级



    string s;
    getline(cin, s);
    s = remove(s); //移除空格

    int n;
    cin >> n;
    cin.ignore();

    vector<string> op(n); //选项
    for(int i = 0; i < n; i++)
    {
        getline(cin, op[i]);
        op[i] = remove(op[i]);
    }

    vector<int> test;
    for(int i = 0; i < 10; i++)
        test.push_back(rand() % 10000);
    
    vector<int> base_v; //题干的表达式预先处理
    auto base_rp = torp(s, prec);

    // for(string x : base_rp) cout << x << endl;

    for(int x : test) 
        base_v.push_back(eval(base_rp, x)); 


    string res;
    for(int i = 0; i < n; i++) //枚举表达式
    {
        auto rp = torp(op[i], prec); //转化成后缀表达式
        bool flag = true; //标记是否等价
        for(int j = 0; j < test.size(); j++)
        {
            int v = eval(rp, test[j]);
            if(v != base_v[j]) {
                flag = false;
                break;
            }
        }
        if(flag) res += (char)('A' + i);
    }
    cout << res << endl;
    return 0;
}


/*
思路:如果直接比较表达式,是否合理?
不合理,因为表达式可能会过于复杂

我们可以通过变量a代入多个不同的值,计算表达式的值是否等价即可。

10个左右的随机数即可。

*/

0 条评论

目前还没有评论...