這玩意兒假啊!
大清早起來突然開始yy,線段樹怎麼區間加乙個等差數列,然後支援區間取max。yy無果,咕咕咕
後來,點開了一道雅禮集訓題,哇塞,真的有這種題哎,哇塞,是弱化版哎(只要支援單點取max就好了),但我還是不會做哎,涼涼涼。
進入正文,思想主要是每個區間用乙個「暴露」最多的線段進行替代,其餘的線段用乙個陣列記下來(因為是單點最值所以可以直接比較)。然後在加入線段的時候分類討論一下:
1、新線段完全高於舊線段,那麼把舊線段丟到陣列裡並覆蓋。
2、新線段完全低於舊線段,那麼直接無視。
3、新舊線段有交點,按交點分治下去。
時間複雜度:\(o(n log^2 n)\)
/*
bzoj3165
*/#include#include#include#include#includeusing namespace std;
const int mod1 = 39989;
const int mod2 = 1000000000;
const int maxn = 100000 + 10;
const int maxt = maxn << 2;
const double eps = 1e-9;
struct anode
anode(int _xa, int _ya, int _xb, int _yb):xa(_xa), ya(_ya), xb(_xb), yb(_yb)
else
}inline double f(int x)
}a[maxn];
inline int sgn(double x)
inline int cross(int x, int y)
//sgt
int n, t[maxt], pos[maxn], tot;
inline void updata(int x, int id) }
void ins(int u, int l, int r, int p, int q, int id)
int l = sgn(a[t[u]].f(l) - a[id].f(l)) < 0;
int r = sgn(a[t[u]].f(r) - a[id].f(r)) < 0;
if(l && r) t[u] = id;
else if(!l && !r)
else
if(tmp > mid && l)
if(tmp > mid && r) ins(rs,mid + 1,r,p,q,id);
}return;
}int mid = (l + r) >> 1;
if(p > mid) ins(rs,mid + 1,r,p,q,id);
else if(q < mid + 1) ins(ls,l,mid,p,q,id);
else }
inline int merge(int x, int y, int k)
int query(int u, int l, int r, int p)
else }
int main()
lastans = tmp;
printf("%d\n", lastans);
}if(op == 1)
}return 0;
}
李超線段樹
首先來看一道題 heoi2013 segment 可以發現的是,實質上某個 x k 處的最大值只有乙個,因此我們需要盡可能減少計算不優的線段。那麼對於兩條線段 a,b a ne b 它們左右端點橫座標相同,就只會產生如下四種情況 從特殊情況出發,每次我們都插入一條 1,n 的線段。如果是前兩條情況,...
李超線段樹
t4正解李超線段樹?不會,滾過來學 貌似思路並不是很難的亞子 我們可以使用權值線段樹!對於每個區間,我們維護乙個最優線段 顯然對於乙個線段完全覆蓋的區間我們才處理 分四種情況討論 直接賦值 直接賦值 直接滾粗 最複雜的情況,我們考慮將覆蓋該區間最長的線段保留為最優線段 欸嘿?怎麼搞呢?其實只需判斷該...
李超線段樹
可以處理二維平面上加入線段,然後查詢單點最大值。首先我們定義乙個區間的最優勢線段,為區間中點值最大的線段,然後我們發現處理詢問,我們只需要將經過的線段樹節點上的最優勢線段對應的點值取max即可。然後考慮如何處理修改,首先將線段劃分到 o logn 個線段樹節點上。如果當前線段被最優勢線段完全覆蓋,那...