題目連線:
又看到了幾個月前做的題,感覺那時候就是個sb
也怪自己剛開始沒搞清楚線段樹,,瞎摸索
用連續線段樹很好理解這個題,之前的**稍微改了一下就好理解多了
1 #include2 #include3 #include4view code#define lson l,m,rt<<1
5#define rson m,r,rt<<1|1
6using
namespace
std;
7const
int maxn=210; //
需要離散的x座標數
8int cnt[maxn<<2]; //
標記該線段是否被選
9double sum[maxn<<2]; //
被選擇的部分線段總長度
10double x[maxn<<2]; //
離散化11
struct
seg12
17 seg(double l,double r,double h,int
s):l(l),r(r),h(h),s(s){}
18bool
operator
< (const seg &cmp) const
1922
}ss[maxn];
2324
void pushup(int rt,int l,int
r)25
3031
void update(int l,int r,int c,int l,int r,int
rt)32
39int m=(l+r)>>1;40
if(l
41if(m
42pushup(rt,l,r);43}
44int bin(double key,int n,double
x)45
54return -1;55
}56intmain()
5771 sort(x,x+m);
72 sort(ss,ss+m);
73//
離散化74
int k=1;75
for(int i=1;i)
76if(x[i]!=x[i-1]) x[k++]=x[i];
7778 memset(cnt,0,sizeof
(cnt));
79 memset(sum,0,sizeof
(sum));
80double ans=0;81
for(int i=0;i1;i++) //
最上面的線段不用處理
8288 printf("
test case #%d\ntotal explored area: %.2lf\n\n
",++cas,ans);89}
90return0;
91 }
下面的可以不看了。。。。。。
看了很久別人的**才理解。。
最重要的一點是要搞清楚線段樹節點的意義:節點記錄的是 該節點到後乙個節點之間的線段長度
從0開始計數
例如: 節點0-0,記錄的是第0個點到第1個點之間線段的長度,即第一條線段的長度
節點1-2,記錄的是第1個點到第3個點之間線段的長度,即第2和第3條線段的長度
關於線段樹節點的理解,不管是要維護什麼資訊,必須是乙個點代表乙個資訊(模擬最開始學習時維護的陣列,乙個下標代表乙個需要維護的值)
每個節點(乙個區間)中包含多個點,葉子含乙個點
所以這裡用線段的左端點代表這條線段,而不能用區間表示線段
1 #include2 #include3 #include4#define lson l,m,rt<<1
5#define rson m+1,r,rt<<1|1
6using
namespace
std;
7const
int maxn=210; //
需要離散的x座標數
8int cnt[maxn<<2]; //
標記該線段是否被選
9double sum[maxn<<2]; //
被選擇的部分線段總長度
10double x[maxn<<2]; //
離散化11
struct
seg12
17 seg(double l,double r,double h,int
s):l(l),r(r),h(h),s(s){}
18bool
operator
< (const seg &cmp) const
1922
}ss[maxn];
2324
void pushup(int rt,int l,int
r)25
3031
void update(int l,int r,int c,int l,int r,int
rt)32
39int m=(l+r)>>1;40
if(l<=m) update(l,r,c,lson);
41if(m
42pushup(rt,l,r);43}
44int bin(double key,int n,double
x)45
54return -1;55
}56intmain()
5771 sort(x,x+m);
72 sort(ss,ss+m);
73//
離散化74
int k=1
;
75for(int i=1;i)
76if(x[i]!=x[i-1]) x[k++]=x[i];
7778 memset(cnt,0,sizeof
(cnt));
79 memset(sum,0,sizeof
(sum));
80double ans=0;81
for(int i=0;i1;i++) //
最上面的線段不用處理
8288 printf("
test case #%d\ntotal explored area: %.2lf\n\n
",++cas,ans);89}
90return0;
91 }
hdu1542(線段樹 掃瞄線)
裸的掃瞄線,學習掃瞄線的題目。具體掃瞄線的原理我不講了,我是看大神們的部落格懂得,就算寫也沒大神屌。下面我給出我的 裡面的注釋是我認為比較重要的地方 include include include includeusing namespace std const int max 210 int n ...
hdu 1542 掃瞄線 線段樹
題目大意 求矩形面積的並 思路 按y軸排序,然後將x投影到線段樹上做乙個線段覆蓋問題即可 注意 為了避免重複,線段座標右端點是開區間,更新時需要加上1 include include include include include define fo i,a,b for int i a i b i ...
HDU 1542 掃瞄線 線段樹優化
有些需要說明的地方 以前寫線段樹時線段樹的每個葉節點為乙個數字,代表乙個區域 7 代表第七個單位長度區域 本題不同在於,最小單位區域必須有兩點代表 2 3 代表從2到3 的乙個區域 上篇掃瞄線演算法複雜度為o n 2 本題用離散化法加線段樹優化為nlog n include include incl...