#include
#include
using namespace std;
//題目中給的p
int p;
//暫存數列的陣列
long long a[100007];
//線段樹結構體,v表示此時的答案,mul表示乘法意義上的lazytag,add是加法意義上的
struct nodest[400007];
//buildtree
void bt(int root, int l, int r)
else
st[root].v%=p;
return ;
}//核心**,維護lazytag
void pushdown(int root, int l, int r)
//update1,乘法,stdl此刻區間的左邊,stdr此刻區間的右邊,l給出的左邊,r給出的右邊
void ud1(int root, int stdl, int stdr, int l, int r, long long k)
//假如給出的區間包含本區間
if(l<=stdl && stdr<=r)
//假如給出的區間和本區間有交集,但是也有不交叉的部分
//先傳遞lazytag
pushdown(root, stdl, stdr);
intm=(stdl+stdr)/2;
ud1(root*2, stdl, m, l, r, k);
ud1(root*2+1, m+1, stdr, l, r, k);
st[root].v=(st[root*2].v+st[root*2+1].v)%p;
return ;
}//update2,加法,和乘法同理
void ud2(int root, int stdl, int stdr, int l, int r, long long k)
if(l<=stdl && stdr<=r)
pushdown(root, stdl, stdr);
intm=(stdl+stdr)/2;
ud2(root*2, stdl, m, l, r, k);
ud2(root*2+1, m+1, stdr, l, r, k);
st[root].v=(st[root*2].v+st[root*2+1].v)%p;
return ;
}//訪問,和update一樣
long long query(int root, int stdl, int stdr, int l, int r)
if(l<=stdl && stdr<=r)
pushdown(root, stdl, stdr);
intm=(stdl+stdr)/2;
return (query(root*2, stdl, m, l, r)+query(root*2+1, m+1, stdr, l, r))%p;
}int main()
bt(1, 1, n);
while(m--)
else
if(chk==2)
else
}return
0;}
線段樹 區間加乘區間最大
如題,已知乙個數列,你需要進行下面兩種操作 1.將某區間每乙個數加上x 2.將某區間每乙個數乘上x 3.求出某區間每乙個數的和 第一行包含三個整數n m p,分別表示該數列數字的個數 操作的總個數和模數。第二行包含n個用空格分隔的整數,其中第i個數字表示數列第i項的初始值。接下來m行每行包含3或4個...
維護序列(線段樹維護區間乘 區間加)
給定乙個長度為n的原序列和模數mod,m個操作,a,b 區間乘c,a,b 區間加c,統計 a,b 的區間和。思路 線段樹維護的還是區間和,但是這裡我們需要用到兩個懶標記,乙個記錄加法,乙個記錄乘法,乘法懶標記下傳之後要重置為1而不是0。對於乙個乘法操作,他影響的是區間和還有這個區間的加法標記 乘法標...
UOJ 56 線段樹區間加和乘
題目描述 如題,已知乙個數列,你需要進行下面兩種操作 1.將某區間每乙個數加上x 2.將某區間每乙個數乘上x 3.求出某區間每乙個數的和 輸入描述 第一行包含三個整數n m p,分別表示該數列數字的個數 操作的總個數和模數。第二行包含n個用空格分隔的整數,其中第i個數字表示數列第i項的初始值。接下來...