这题最开始的时候看到线段树吧,没找到好的做法

想了下既然是乘积和

(-)

(--)

(---)

在脑子里就是这种线条位于各个位置,然后各种长度代表连续的乘积个数

然后把所有情况累加起来,但是并不好算

这题每次单点修改最开始就想到肯定是算贡献

然后总和是所有连续积和

然后就想是不是能用到前缀积呢,然后发现修改a[p] ai...ap...aj 1<=i<=p && n=>j>=p

(--ap---)

(-ap--)

然后分配律化简下,就是ap的后缀积和ap右边一位的前缀积和,这就是贡献

但是我直接把先算树的节点用前缀积表示pre[p]表示到p的前缀积,然后修改a[p]的时候就是修改p到n记录之前值改为现在的,就相当于
a[p]/a[p],a[p]是以前的

但是不好处理为0的情况以前为0.就。。。后面看了别人的发现可以算总和,前后缀积也可以分区间分节点向上推倒

#include <cstdio>
#include <memory>
#include <cstdlib>
#include <cstring>
#include <cmath>
#include <vector>
#include <cassert>
#include <string>
#include <ctime>
#include <map>
#include <queue>
#include <algorithm>
#include <iostream>
#include <cassert>
using namespace std;
#define REP(i,n) for(int i=0;i<n;i++)
#define rep(i,a,b) for(int i=a;i<=b;i++)
#define req(i,a,b) for(int i=a;i>=b;i--)
#define rp(i,a) for(int i=head[a];i+1;i=edge[i].next)
#define cl(a,b) memset(a,b,sizeof a);
#define ll long long
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
#define mod 10007
const int inf = ~0u >> 2;
const ll INF = (1LL << 62) - 1;
double eps = 1e-9;
const int N = 1e6 + 5;
const int M = 21; int ans, cnt;
vector<int>g[N];
int n, m;
int in[N];
map<string, int>mp;
string S[N]; int pre[N];
int suf[N];
int sum[N];
int mul[N];
void up(int rt) {
mul[rt] = (mul[rt << 1] * mul[rt << 1 | 1]) % mod;
pre[rt] = (pre[rt << 1] + pre[rt << 1 | 1 ] * mul[rt << 1]) % mod;
suf[rt] = (suf[rt << 1 | 1] + suf[rt << 1] * mul[rt << 1 | 1]) % mod;
sum[rt] = (sum[rt << 1] + sum[rt << 1 | 1] + suf[rt << 1] * pre[rt << 1 | 1]) % mod;
}
void build(int l, int r, int rt) {
mul[rt] = pre[rt] = suf[rt] = sum[rt] = 0;
if (l == r) {
//scanf("%d", &c[rt]);
return;
}
int m = (l + r) >> 1;
build(l, m, rt * 2);
build(m + 1, r, rt * 2 + 1);
up(rt);
}
void update(int p, int value, int l, int r, int rt) {
if (l == r) {
if (l != p)
return;
pre[rt] = value%mod+mod;
suf[rt] = value%mod+mod;
sum[rt] = value%mod+mod;
mul[rt] = value%mod+mod;
return;
}
int m = (l + r) >> 1;
if (p <= m)
update(p, value, lson);
if (m < p)
update(p, value, rson);
up(rt);
}
int main() {
while (~scanf("%d%d", &n, &m)) {
build(1, n, 1);
ans = 0;
while (m--) {
int op, l, r;
int p, val;
scanf("%d%d", &p, &val);
update(p, val, 1, n, 1);
printf("%d\n", sum[1]);
}
}
return 0;
}

最新文章

  1. 【Alpha】Daily Scrum Meeting第六次
  2. js前台加密,java后台解密实现
  3. java导入excel时遇到的版本问题
  4. 如何激活webstorm 11
  5. Java基础之访问文件与目录——列出目录内容(ListDirectoryContents)
  6. SHELL:Find Memory Usage In Linux (统计每个程序内存使用情况)
  7. MacOS下的生活——RescueTime,时间规划利器
  8. golang 性能
  9. LinkButton和HyperLink的页面跳转用法
  10. NHIBERNATE之映射文件配置说明(转载4)
  11. 如何在HTTP头中隐藏PHP版本号
  12. LeetCode之旅(22)-House Robber
  13. jQuery 练习:tab 切换
  14. 安全系列之CSRF初探
  15. [lightoj P1151] Snakes and Ladders
  16. python 多返回值
  17. 基于VS2017的Docker Support体检ASP.NET Core站点的Docker部署
  18. kafka基本原理概述——patition与replication分配
  19. Oracle自治事务实际用例
  20. CoreData 增删改查

热门文章

  1. Android html5和Android之间的交互
  2. 面经手册 &#183; 第2篇《数据结构,HashCode为什么使用31作为乘数?》
  3. Linux学习笔记之如何在图形界面旁边把终端添加显示出来
  4. spring data jpa 代码生成!!(精华帖)
  5. 【工具】之003-Windows下常用工具
  6. Codechef May Challenge 2020 Division 1 记录
  7. .Net微服务实战之Kubernetes的搭建与使用
  8. Mybatis-08-动态SQL
  9. GitHub标星120K+的JDK并发编程指南,连续霸榜GitHub终于开源了
  10. JAVA HTML 以压缩包下载多文件