nyoj 1068
題目鏈結
題目意思; 典型的線段樹,插線問線.不過多了乙個,
a 操作某乙個區間乙個數整體加上乙個數;
s 操作查詢某乙個區間的總和,
q 操作,查詢這個區間有多少個奇數.
下面是 線段樹延遲更新,奇數的個數更新時注意
如果變化的是奇數,那麼 : 現在區間奇數個數=區間長度-原本區間的奇數個數.
下面 延遲更新 模板題目.如果對模板不太理解,請看這個博
或者看**注釋
延遲更新大致思想: 每一次資料更新, [a,b] 區間,則只需要更新到他們的子區間且 滿足各個子區間無交集 且 並集為區間 [a,b];每次更新,都更新到這些子區間停止,遞迴歸的時候再更新上面的值. 查詢的時候mark,標記的是上次更新到這裡停止了,如果要往下走,標記下沉,並計算左右兒子.
#include#include#include#include#include#include#include#include#include#include#include#include#include#include#include#includeusing namespace std;
typedef long long ll;
const int inf=2e9+1e8;
const int mod=1e9+7;
const int maxsize=1e6+5;
const double eps=0.0000000001;
void fre()
#define memst(a,b) memset(a,b,sizeof(a))
#define fr(i,a,n) for(int i=a;i>1ll;
if(l==r)
build(l,mid,pos<<1ll);
build(mid+1ll,r,pos<<1ll|1ll);
//上面是遞的過程,下面是歸並且求和;
tree[pos].sum=tree[pos<<1ll].sum+tree[pos<<1ll|1ll].sum;
tree[pos].odd=tree[pos<<1ll].odd+tree[pos<<1ll|1ll].odd;
return ;
}/** pushdown 函式
將本節點的左右孩子節點的標記變數加上自己節點的標記值,
且把計算結果(通常是求和)並把自己的標記值清空
*/void pushdown(ll pos)
tree[pos].mark=0;
}}/** update 函式
插線函式,遞迴開始;
如果找到子區間則,更新當前節點,因為只不需要更新到葉子節點,
所以,計算當前值,把當前節點的標記變數 加上 k,停止遞迴;
否則接著遞迴下去,每次需要下沉標記,並計算;
--> 遞迴
合併左右孩子節點的值,
*/void update(ll l,ll r,ll pos,ll k)
pushdown(pos);
if(mid>1ll;
if(tree[pos].l==l&&tree[pos].r==r)
pushdown(pos);
if(mid
題解 線段樹 關於時間
這是本蒟蒻的原創題 確實很簡單 本蒟蒻loj賬號diogenes 本題的難點在於每個操作會重複多次。核心思想是把第t秒的操作提前到第一秒,再減去多餘的部分。有一種構造方法 ad d i.j add i.j 表示區間 i j i,j 需要加的值。de l i.j del i.j 表示區間 i j i,...
線段樹練習二 題解
線段樹練習二 桌子上零散地放著若干個不同顏色的盒子,桌子的後方是一堵牆。如右圖所示。問從桌子前方可以看到多少個盒子?假設人站得足夠遠 輸入時,由底向上,從左到右 16 桌子長度 5 盒子數量 4 712 14 1 56 10 11 16 output 41 n nn 100000,1 m mm 10...
線段樹練習三 題解
線段樹練習三 給定一條長度為m mm的線段,有n nn個操作,每個操作有3個數字x xx,y yy,z zz表示把區間 x xx,y yy 染成顏色z zz,詢問染完色之後,這條長度為m mm的線段一共有幾種顏色。規定 線段的顏色可以相同。連續的相同顏色被視作一段。問x xx軸被分成多少段。inpu...