權值線段樹

2022-07-15 13:57:18 字數 1135 閱讀 3323

權值線段樹只是節點存的內容變成了權值,區間,區間和,區間數字個數等,和一般線段樹的操作差別不大

但對於某些特定問題來說操作很簡便,值域較大時一般會採用離散化(就只能離線了

可求區間第k大數,逆序對個數等

示例如圖:

//待新增

結構體存

struct

node

tree[n*4]; //開4倍空間

建樹

void

build(ll l, ll r, ll now)

ll mid=(l+r)>>1

; build(l,mid,now

<<1

); build(mid+1,r,now<<1|1

); //左右遞迴建樹

return

;}

插入新點(根據不同問題修改

void

update(ll pos, ll now) //pos為下標,b[pos]存值

if(pos<=tree[now<<1].r) update(pos,now<<1

);

else update(pos,now<<1|1

); tree[now].s=tree[now<<1].s+tree[now<<1|1

].s;

tree[now].num=tree[now<<1].num+tree[now<<1|1

].num;

return

;}

查詢(根據不同問題修改

ll query(ll now, ll k) //查詢求和<=k的最大個數

初始資料處理

for(i=1; i<=n; i++)

sc(a[i]), b[i]=a[i];

sort(b+1,b+1+n);//需排序

build(

1,unique(b+1,b+n+1)-(b+1),1

);//unique去重,初始建樹

ll pos=lower_bound(b+1,b+n+1,a[i])-b;//二分查詢位置( -(b+1)+1=-b )

update(pos,

1);

權值線段樹

維護全域性的值域資訊,每個節點記錄的是該值域的值出現的總次數。使用二分的思想 離散化的時候,需要用到 支援查詢全域性k小值,全域性rank,前驅,後繼等。單詞操作時間複雜度為o logn 空間複雜度為o n 相對於平衡樹的優勢 簡單,速度快 劣勢 值域較大時,我們需要離散化,變成離線資料結構 我認為...

權值線段樹

include using namespace std int n,m,tre 10003 4 laz 10003 4 void pushdown int num void update int num,int le,int ri,int x,int y,int z pushdown num int...

權值線段樹

權值線段樹是線段樹的一種,但是它與線段樹不同 線段樹的每個結點是用來維護一段區間的最大值或總和 而權值線段樹的每個結點儲存的一段區間有多少個數 權值線段樹主要用來查詢區間第k大或者第k小的值 現在有乙個陣列x 10 對陣列排序後為x 10 每個數的個數如下 1 32 2 3 24 1 5 18 1 ...