線段樹模板(洛谷P3372)

2022-08-11 01:15:13 字數 2100 閱讀 2138

給定序列,支援區間加、求區間和。

線段樹的基本思路(線段樹模板嘛,不懂得看題解第一,dalao講解超詳細的)

#includeusing namespace std;

#define ll long long

int maxn=1000001;

unsigned ll n,m,a[maxn],ans[maxn<<2],lazytag[maxn<<2];

開頭還用解釋嗎qaq

inline ll 左兒子

inline ll 右兒子

void 輸入

void 傳遞

void 建樹

void 當前處理懶標記

void 傳遞懶標記

void 更新

ll 求和

//當然在資料較小的時候可以用int,看著順眼

以上是各函式的框架,都是線段樹的基本函式。

int main()

case 2: }

return 0;

}

主函式的設計思路還是比較簡單的,不過要注意輸入輸出的優化,cincout可能會tle吧,雖然沒試過2333

接下來是填好了的主函式!一定要自己打一遍再看哦~

真的自己打了嗎???

int main()

case 2:

return 0;

}

這些函式都是啥???接著往下看吧owo

先看比較簡單的找左右兒子

根據二叉樹的性質

父親節點fa的左右兒子

分別是 fa<<2 和 fa<<2|1

這是zhaungbi優秀的位運算

表示fa2 和 fa2+1

你可以先不用理解它是什麼意思

記住它的含義就好了

void shuru()

簡單可愛的輸入

void pushup(ll x)

void buildtree(int x,int l,int r)

ll mid=(l+r)>>1;

build(leftchild(x),l,mid);

build(rightchild(x),mid+1,r);

pushup(p);

}

二分的方法建樹

如果是葉子節點,那麼它的值就是自己

如果是父親節點,就是它的兒子的和

初始化懶標記為0,表示暫時沒有向下傳遞的資料

void lazy(ll x,ll l,ll r,ll k)

void pushdown(ll x,ll l,ll r)

void update(ll l,ll r,ll l,ll r,ll x,ll k)

//不完全包含

pushdown(x,l,r);//處理懶標記,排除影響

ll mid=(l+r)>>1;

if(l<=mid)update(l,r,l,mid,leftchild(x),k);

if(r>mid) update(l,r,mid+1,r,rightchild(x),k);

pushup(x);

}ll querysum(ll a,ll b,ll l,ll r ll x)

接下來求和和更新的操作類似

都是判斷所求區間與當前區間的包含關係

完全包含當前區間比較好辦

不完全包含的情況用二分查詢,降低時間複雜度owo

嘛測試點資訊

洛谷P3372 線段樹模板

線段樹講的很詳細的部落格 鏈結 includeusing namespace std typedef long long ll const int maxn 100005 ll dat maxn 儲存資料 ll tree maxn 2 儲存線段樹的陣列常開成資料的4倍大小 ll add maxn 2...

洛谷 P3372 線段樹 模板1

模板一是區間加修改和區間和 例題 如下 include includeusing namespace std struct tree int rt 1,cnt 2 int n,i,m const int maxa 100000 tree tree maxa 1 結構體模擬線段樹 long long ...

洛谷 P3372 模板 線段樹 1

題目描述 如題,已知乙個數列,你需要進行下面兩種操作 1.將某區間每乙個數加上x 2.求出某區間每乙個數的和 輸入格式 第一行包含兩個整數n m,分別表示該數列數字的個數和操作的總個數。第二行包含n個用空格分隔的整數,其中第i個數字表示數列第i項的初始值。接下來m行每行包含3或4個整數,表示乙個操作...