線段樹 動態最值

2021-07-13 03:27:41 字數 2424 閱讀 9179

乍一看這題是乙個陣列和鍊錶的結合體,想到用塊狀鍊錶,但是計算一下時間代價是109

會超時(這裡我同學寫了,果然超時,詳情見傳送門),然後乍一瞅區間最值,也許是線段樹,但是又不會刪除,就懵逼了。。

後來才知道,原來線段樹也可以支援刪除節點,只需要在原來的儲存方式上變化一下就好了。

做法:把原來的幾點存區間左右邊界變成類似平衡樹那樣的存節點size,然後查詢的時候比較左右節點的size和當前要查詢的點號就行:

查詢分三種情況:

1. 查詢區間左端點比當前左節點的size小,右端點比做節點size大,證明區間在左右子樹中,分別查詢。

2. 查詢區間左端點比左子節點size小,右端點比左子節點size小,查左子樹。

3. 查詢區間左端點比左子節點size大,右子節點也比它大,查右子樹。

刪除分兩種:

1. 刪除number比左size小,遞迴左;

2. 刪除number比左大,遞迴右;

然後就沒了。。。。線段樹好流弊啊。。。

**

#include 

#include

#include

#define inf 0x7fffffff

#define maxn 1000100

using namespace std;

int in[maxn];

int ansmin=inf,ansmax=-inf;

struct segment_tree;

node tree[maxn*4];

void pre(int n)

void build(int left,int right,int root)

int mid=(left+right)>>1;

build(left,mid,root*2);

build(mid+1,right,root*2+1);

tree[root].num=tree[root*2].num+tree[root*2+1].num;

tree[root].minn=min(tree[root*2].minn,tree[root*2+1].minn);

tree[root].maxx=max(tree[root*2].maxx,tree[root*2+1].maxx);

}void query(int left,int right,int root)

int n1=tree[root*2].num;

int n2=tree[root*2+1].num;

if(left<=n1&&right>n1)

else

if(left<=n1&&right<=n1) query(left,right,root*2);

else

if(left>n1&&right<=n1+n2) query(left-n1,right-n1,root*2+1);

}void del(int num,int root)

int n1=tree[root*2].num;

int n2=tree[root*2+1].num;

if(num<=n1) del(num,root*2);

else del(num-n1,root*2+1);

tree[root].num=tree[root*2].num+tree[root*2+1].num;

tree[root].minn=min(tree[root*2].minn,tree[root*2+1].minn);

tree[root].maxx=max(tree[root*2].maxx,tree[root*2+1].maxx);

}}s;int main()

else

if(a==2)

}return

0; }

時間

正在測試 minmax.0(minmax.0.in)… 正確 0.082秒

正在測試 minmax.1(minmax.1.in)… 正確 0.088秒

正在測試 minmax.2(minmax.2.in)… 正確 0.087秒

正在測試 minmax.3(minmax.3.in)… 正確 0.079秒

正在測試 minmax.4(minmax.4.in)… 正確 0.093秒

正在測試 minmax.5(minmax.5.in)… 正確 0.630秒

正在測試 minmax.6(minmax.6.in)… 正確 0.888秒

正在測試 minmax.7(minmax.7.in)… 正確 1.417秒

正在測試 minmax.8(minmax.8.in)… 正確 1.172秒

正在測試 minmax.9(minmax.9.in)… 正確 2.121秒

動態區間最值(RMQ) 線段樹

建樹 a aa陣列為初始陣列,tre etree tree 陣列為樹 typedef long long ll const int inf 0x7fffffff const int maxn 2e5 10 int a maxn int tree maxn 2 lz maxn 2 建樹函式 和普通線段...

線段樹,區間最值

codeforces 91b queue 線段樹,區間最值 題意是,對於給定區間內的每個元素,要求求出離他最遠的那個元素之間的距離。可以維護乙個線段樹的最小值,每次對於乙個元素,查詢其最右邊的元素的位置。include include include includeusing namespace s...

區間最值與線段樹

區間最值問題 有如下無序序列,求任意子區間段的最大值。接著,我們要用分治的思想來快速地解決上面的問題。在解決問題之前,先介紹一些分治的概念。二分查詢 二分查詢是分治思想的典型運用 我們有如下序列 a1,a2,a3 an.要查詢其中等於b的元素。一種方法就是乙個個對比,看看是不是相等,時間複雜度為n。...