| ||||||||||
| Online Judge | Problem Set | Authors | Online Contests | User | ||||||
|---|---|---|---|---|---|---|---|---|---|---|
| Web Board Home Page F.A.Qs Statistical Charts | Current Contest Past Contests Scheduled Contests Award Contest | |||||||||
晕,我的线段树超时!我是把每个节点保存最大最小值。每次动态访问求得该线段的最大最小值。然后求差! 为什么会超时?有空的就帮小弟看看代码:
#include<stdio.h>
#include<string.h>
#include<algorithm>
using namespace std;
struct tree
{
int l,r,len,max,min;
}a[200000];
int h[50010];
void init(int l,int r,int v) // 初始化
{
a[v].l=l;
a[v].r=r;
a[v].max=0;
a[v].min=0x7FFFFFFF;
if(l==r)
{
a[v].len=1;
return;
}
a[v].len=r-l+1;
init(l,(l+r)/2,v*2);
init((l+r)/2+1,r,v*2+1);
}
void insert(int d,int v,int w) // 插入线段
{
if(a[w].l==a[w].r)
{
a[w].max=v;
a[w].min=v;
return;
}
if(a[w].max<v)
a[w].max=v;
if(a[w].min>v)
a[w].min=v;
if(a[2*w].len>d)
{
insert(d,v,2*w);
}
else
{
insert(d-a[2*w].len,v,2*w+1);
}
}
int qmax(int l,int r,int w) //求最大值
{
int max=0;
if(a[w].l==l && a[w].r==r)
{
return a[w].max;
}
if(l>(a[w].l+a[w].r)/2)
return qmax(l,r,w*2+1);
else if(r<=(a[w].r+a[w].l)/2)
return qmax(l,r,2*w);
max=max>qmax(l,(a[w].l+a[w].r)/2,2*w)?max:qmax(l,(a[w].l+a[w].r)/2,2*w);
max=max>qmax((a[w].l+a[w].r)/2+1,r,2*w+1)?max:qmax((a[w].l+a[w].r)/2+1,r,2*w+1);
return max;
}
int qmin(int l,int r,int w) // 求最小值
{
int min=0x7FFFFFFF;
if(a[w].l==l && a[w].r==r)
{
return a[w].min;
}
if(l>(a[w].l+a[w].r)/2)
return qmin(l,r,w*2+1);
else if(r<=(a[w].r+a[w].l)/2)
return qmin(l,r,2*w);
min=min<qmin(l,(a[w].l+a[w].r)/2,2*w)?min:qmin(l,(a[w].l+a[w].r)/2,2*w);
min=min<qmin((a[w].l+a[w].r)/2+1,r,2*w+1)?min:qmin((a[w].l+a[w].r)/2+1,r,2*w+1);
return min;
}
int main()
{
int i,j,k,l,n,m,s,min,max;
while(scanf("%d%d",&n,&m)==2)
{
init(1,n,1);
for(i=0;i<n;i++)
{
scanf("%d",&s);
insert(i,s,1);
}
for(i=1;i<=m;i++)
{
scanf("%d%d",&k,&l);
max=qmax(k,l,1);
min=qmin(k,l,1);
printf("%d\n",max-min);
}
}
return 0;
}
Followed by:
Post your reply here: |
All Rights Reserved 2003-2013 Ying Fuchen,Xu Pengcheng,Xie Di
Any problem, Please Contact Administrator