CodeForces 138C Mushroom Gnomes - 2 (線段樹)
阿新 • • 發佈:2018-11-04
題意
給你n個蘑菇和m顆大樹的位置,以及大樹往左倒往右倒的概率,大樹的高度,和蘑菇的權值,蘑菇被壓倒必死,問你蘑菇不被壓死的權值的最大的期望是多少?
思路
對於一顆樹而言,他往左倒的概率是
那麼不往左倒的概率就是
,那麼我們線段樹維護一下某個區間不被壓倒(樹不會倒)的概率就好了,具體怎麼維護,我們還是把所有點離散存下來,之後以離散後的點為區間建立線段樹節點原來都是1,之後更新每個區間不被壓倒的概率就好了,最後我們把權值*概率就行了。
ps:線段樹謎之開點,開了尼瑪16倍,,,
程式碼
#include <bits/stdc++.h>
using namespace std;
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
const int maxn = 1e5+10;
struct Tree
{
int pos,h;
double l,r;
}Tree[maxn];
struct Mush
{
int pos,val;
}mush[maxn];
int Hash[maxn<<4];
double tree[maxn<<4];
int n , m;
void build(int l,int r,int rt)
{
tree[rt] = 1;
if(l == r) return ;
int m = (l+r)>>1;
build(lson);
build(rson);
}
void update(int L,int R,double val,int l,int r,int rt)
{
if(l>=L && R >= r)
{
tree[rt] *= val;
return ;
}
int m = (l+r)>>1;
if(m >= L) update(L,R,val,lson);
if(R > m) update(L,R,val,rson);
}
double query(int pos,int l,int r,int rt)
{
if(l == r) return tree[rt];
int m = (l+r)>>1;
if(m >= pos) return tree[rt] * query(pos,lson);
else return tree[rt] * query(pos,rson);
}
int main()
{
scanf("%d%d",&n,&m);
int x,y;
int cnt = 0;
for(int i = 0 ; i < n ; i++)
{
scanf("%d%d%d%d",&Tree[i].pos,&Tree[i].h,&x,&y);
Tree[i].l = x/100.0,Tree[i].r = y/100.0;
Hash[cnt++] = Tree[i].pos-1;
Hash[cnt++] = Tree[i].pos + Tree[i].h;
Hash[cnt++] = Tree[i].pos + 1;
Hash[cnt++] = Tree[i].pos - Tree[i].h;
}
for(int i = 0 ; i < m ; i++)
{
scanf("%d%d",&mush[i].pos,&mush[i].val);
Hash[cnt++] = mush[i].pos;
}
sort(Hash,Hash+cnt);
cnt = unique(Hash,Hash+cnt) - Hash;
build(1,cnt,1);
for(int i = 0 ; i < n ; i++)
{
int mid1 = lower_bound(Hash,Hash+cnt,Tree[i].pos-1) - Hash + 1;
int mid2 = lower_bound(Hash,Hash+cnt,Tree[i].pos+1) - Hash + 1;
int l = lower_bound(Hash,Hash+cnt,Tree[i].pos - Tree[i].h) - Hash + 1;
int r = lower_bound(Hash,Hash+cnt,Tree[i].pos + Tree[i].h) - Hash + 1;
update(l,mid1,(1.0-Tree[i].l),1,cnt,1);
update(mid2,r,(1.0-Tree[i].r),1,cnt,1);
}
double ans = 0;
for(int i = 0 ; i < m ; i++)
{
int pos = lower_bound(Hash,Hash+cnt,mush[i].pos) - Hash + 1;
ans += query(pos,1,cnt,1) * mush[i].val;
}
printf("%.10f\n",ans);
}