该场比赛反应出基础不牢靠的现象
T
3
T3
T3-将式子等价变形,用乘代替除()避免下取整和浮点数导致的精度误差
T4-巫师的总力量和
- 考虑以每个巫师为末尾的子数组。需要在左侧查找第一个小于的数
- 使用单调栈(忘记了)
- 注意该取模的地方才取模
class Solution {
typedef long long ll;
const long long mod = (ll) (1e9 + 7);
public:
ll getrangesum(ll pre[],int i,int j)
{
ll pre_; if(i == 0) pre_ = 0;else pre_ = pre[i - 1];
return (pre[j]- pre_ );
}
int totalStrength(vector<int>& strength) {
stack<array<ll,3>> s;
//计算后缀
ll suf[strength.size()];
//计算前缀和
ll pre[strength.size()];
for(int i = 0;i<strength.size();i++)
{
ll pre_;
if(i == 0) pre_ = 0;else pre_=suf[i-1];
suf[i] = (pre_ + ((ll)i + 1) * (ll)strength[i]) ;
if(i == 0) pre_ = 0;else pre_ = pre[i-1];
pre[i] = (pre_ + (ll)strength[i]);
//cout << pre[i] << endl;
}
ll dp[strength.size()];
//对每个点使用单调栈维护
for(int i = 0;i<strength.size();i++)
{
while(!s.empty() && s.top()[1] >= strength[i]) s.pop();
if(s.empty())
{
s.push({(ll)i,strength[i],((ll)i+1)*(ll)strength[i]});
dp[i] = (suf[i] % mod * strength[i] % mod) % mod;
}
else
{
array<ll,3> temp = s.top();
ll j = temp[0];
ll newsum = (i - j) * (ll)strength[i] + temp[2];
ll sum_j = temp[2];
ll sum_j_1_i = getrangesum(pre,j+1,i);
ll suf_j_1_i = getrangesum(suf,j+1,i);
dp[i] = ((dp[j] + (sum_j % mod )*(sum_j_1_i % mod)) % mod + ((suf_j_1_i % mod - (j + 1) * (sum_j_1_i % mod) % mod)%mod * (ll)strength[i] % mod) % mod) % mod;
s.push({(ll)i,(ll)strength[i],newsum});
}
// cout << dp[i] << endl;
}
long long ans = 0;
for(int i = 0;i<strength.size();i++) ans = (ans + dp[i]) % mod;
return (int)(ans % mod);
}
};