CCF网站不保存题解,在此记录AC答案,方便日后复习回看。
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
ll MOD = 1e9 + 7;
struct item { //一项,包含系数和多个自变量的乘积
map<int, int>mp; //分别表示下标和次数
ll coe;
item(map<int, int>mp, ll coe): mp(mp), coe(coe) {}//构造函数
};
struct formula {
vector<item>vec;
formula(vector<item>vec): vec(vec) {}
};
stack<formula>st;//用来储存运算过程中的多项式,formula是因为可能取出的也是多项式
vector<ll>value;
ll stringToInt(string s) {
ll sum = 0;
for (int i = (s[0] == '-') ? 1 : 0; i < s.length(); i++)
sum = sum * 10 + s[i] - '0';
return (s[0] == '-') ? -1 * sum : sum;
}
item mul(item a, item b) {//项与项之间的乘法
ll coe = a.coe * b.coe;
map<int, int>mpmul;
map<int, int>::iterator i;
for (i = a.mp.begin(); i != a.mp.end(); i++) {
mpmul[i->first] = a.mp[i->first] + b.mp[i->first];
b.mp.erase(i->first);
}
for (i = b.mp.begin(); i != b.mp.end(); i++)
mpmul[i->first] = b.mp[i->first];
return item(mpmul, coe);
}
formula addf(formula a, formula b) { //多项式相加
for (auto i : b.vec)
a.vec.push_back(i);
return a;
}
formula subtractf(formula a, formula b) { //多项式相减,此处写的是b-a(b先进,后弹出)
for (auto &i : a.vec)
i.coe *= -1;
return addf(a, b);
}
formula multiplef(formula a, formula b) { //多项式相乘
vector<item>vec;
for (auto i : a.vec)
for (auto j : b.vec) {
vec.push_back(mul(i, j));
}
return formula(vec);
}
ll functionf(formula a, int goal) { //求导 顺便代值
ll sum = 0;
ll mul;
for (auto i : a.vec) {//i是个item,有coe和mp,item中有被求导的自变量才有计算价值,否则一求导就是0
mul = 0;
if (i.mp.find(goal) != i.mp.end()) {
mul = (i.coe * i.mp[goal]) % MOD;
i.mp[goal]--;
for (auto j : i.mp) //遍历代值,j是一个pair
for (int k = 0; k < j.second; k++) { //次数为多少就乘几次
mul = (mul * value[j.first]) % MOD;
}
}
sum = (sum + mul) % MOD;
}
return sum;
}
int main() {
int n, m;
cin >> n >> m;
string str, temp;
getchar();
getline(cin, str);
stringstream ss(str);
while (ss >> temp) {
if (temp == "+" || temp == "-" || temp == "*") {
formula a = st.top();//弹出来的都是要参与运算的formula,运算结果也应该包装成formula放进去
st.pop();
formula b = st.top();
st.pop();
if (temp == "+") {
st.push(addf(a, b));
} else if (temp == "-") {
st.push(subtractf(a, b));
} else if (temp == "*") {
st.push(multiplef(a, b));
}
} else {
ll coe = 1;
vector<item>vec;
map<int, int>mp;
if (temp[0] == 'x') {
mp[stringToInt(temp.substr(1, temp.length() - 1))] = 1;
} else {
coe = stringToInt(temp);
}
vec.push_back(item(mp, coe));
st.push(formula(vec));
}
}//走到这一步时,st.top()就是待求导的多项式,遍历求导代值即可
while (m--) {
for (int i = 0; i <= n; i++) {
ll v;
cin >> v;
value.push_back(v);
}
ll ans = functionf(st.top(), value[0]);
cout << ((ans < 0) ? ans + MOD : ans) << endl;
value.clear();
}
return 0;
}