yizimi的前缀积
前缀积?
想的美!!!
此题卡分块(别想混过去),st表,平衡树,,,
时限在那里呐 ~
222ms / 128MB
这时限线段树能过?
可以的。
正解:裸的 线段树
#include <algorithm>
#include <cmath>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <ctime>
#include <iostream>
#include <map>
#include <queue>
#include <set>
#include <stack>
#include <string>
#include <vector>
using namespace std;
#define go(i, j, n, k) for (int i = j; i <= n; i += k)
#define fo(i, j, n, k) for (int i = j; i >= n; i -= k)
#define rep(i, x) for (int i = h[x]; i; i = e[i].nxt)
#define mn 1000010
#define inf 2147483647
#define ll long long
#define ld long double
#define fi first
#define se second
#define root 1, n, 1
#define lson l, m, rt << 1
#define rson m + 1, r, rt << 1 | 1
#define bson l, r, rt
//#define LOCAL
#define Debug(...) fprintf(stderr, __VA_ARGS__)
inline int read(){
int f = 1, x = 0;char ch = getchar();
while (ch > '9' || ch < '0'){if (ch == '-')f = -f;ch = getchar();}
while (ch >= '0' && ch <= '9'){x = x * 10 + ch - '0';ch = getchar();}
return x * f;
}
//This is AC head above...
int n, m, p;
struct tree{
ll x;
};
struct SegmentTree{
tree z[mn << 2];
ll col[mn << 2];
inline void update(int rt){
z[rt].x = (z[rt << 1].x * z[rt << 1 | 1].x) % p;
}
inline tree operation(tree a,tree b){
return (tree){(a.x * b.x) % p};
}
inline void color(int l,int r,int rt,ll v){
z[rt].x += (r - l + 1) * v;
col[rt] += v;
}
inline void push_col(int l,int r,int rt){
if(col[rt]){
int m = (l + r) >> 1;
color(lson, col[rt]);color(rson, col[rt]);
col[rt] = 0;
}
}
inline void build(int l,int r,int rt){
if(l==r){z[rt].x = read();return;}
int m = (l + r) >> 1;build(lson);build(rson); update(rt);
}
inline void modify(int l,int r,int rt,int nowl,int nowr,ll v){
if(nowl<=l && r<=nowr){color(bson, v); return;}
int m = (l + r) >> 1; push_col(bson);
if(nowl<=m) modify(lson, nowl, nowr, v);
if(m<nowr) modify(rson, nowl, nowr, v);
update(rt);
}
inline tree query(int l,int r,int rt,int nowl,int nowr){
if(nowl<=l && r<=nowr) return z[rt];
int m = (l + r) >> 1; push_col(bson);
if(nowl<=m){
if(m<nowr) return operation(query(lson, nowl, nowr), query(rson, nowl, nowr));
else return query(lson, nowl, nowr);
}else return query(rson, nowl, nowr);
}
} tr;
int main(){
n = read(), m = read(), p = read();
tr.build(root);
go(i, 1, m, 1){
int l = read(), r = read();
cout << tr.query(root, l, r).x % p << "\n";
}
#ifdef LOCAL
Debug("My Time: %.3lfms\n", (double)clock() / CLOCKS_PER_SEC);
#endif
return 0;
}
为什么不用前缀积?
题目名字不是前缀积吗?
我用前缀和思想不行吗?
如果你用前缀积,那如何实现一个数除以一个数再同余?
逆元?
看清楚,30%的数据p为质数,
也就是说除了这30%,就不保证是不是质数啦!
不是质数,哪里来的逆元?所以就根本不行的啦。
为什么不用分块
O(n sqrt n),,,
过不过的去1000000你明白的
为什么不用ST表?
据大佬说st表的空间卡的厉害,会爆空间
为什么不用平衡树
我觉得只有dalao才会这么无聊的用平衡树,,,
常数啊,,,
线段树大法好!!!