zoukankan      html  css  js  c++  java
  • POJ

    这个题目是一个典型的RMQ问题,给定一个整数序列,1~N,然后进行Q次询问,每次给定两个整数A,B,(1<=A<=B<=N),求给定的范围内,最大和最小值之差。

    解法一:这个是最初的解法,时间上可能会超时,下面还有改进算法.4969ms

     1 #include<stdio.h>
     2 #include<stdlib.h>
     3 #define INF 1000010
     4 #define max(a,b) ((a)>(b)?(a):(b))
     5 #define min(a,b) ((a)>(b)?(b):(a))
     6 
     7 typedef struct res
     8 {
     9     int mx,mi;
    10 } pair;
    11 
    12 typedef struct node
    13 {
    14     struct node *lc,*rc;
    15     int ld,rd;
    16     pair res;
    17 }  node;
    18 
    19 node *buildTree(int a,int b)
    20 {
    21     node*p=(node*)malloc(sizeof(node));
    22     p->ld=a;
    23     p->rd=b;
    24     p->res.mx=0;
    25     p->res.mi=INF;
    26     p->lc=p->rc=NULL;
    27     if(a==b)
    28         return p;
    29     p->lc=buildTree(a,(a+b)>>1);
    30     p->rc=buildTree(((a+b)>>1)+1,b);
    31     return p;
    32 }
    33 
    34 void insert(node*T,int pos,int key)
    35 {
    36     int mid=(T->rd+T->ld)>>1;
    37     if(T->rd==T->ld)
    38     {
    39         T->res.mx=T->res.mi=key;
    40         return;
    41     }
    42     if(pos<=mid)
    43         insert(T->lc,pos,key);
    44     else insert(T->rc,pos,key);
    45     T->res.mx=max(T->lc->res.mx,T->rc->res.mx);
    46     T->res.mi=min(T->lc->res.mi,T->rc->res.mi);
    47     return;
    48 }
    49 
    50 pair search(node*T,int a,int b)
    51 {
    52     pair  temp1,temp2,ans;
    53     int mid=(T->rd+T->ld)>>1;
    54 
    55     temp1.mx=temp2.mx=0;
    56     temp1.mi=temp2.mi=INF;
    57     if(a<=T->ld&&T->rd<=b)
    58         return T->res;
    59     if(a<=mid)
    60         temp1=search(T->lc,a,b);
    61     if(b>mid)
    62         temp2=search(T->rc,a,b);
    63     ans.mx=max(temp1.mx,temp2.mx);
    64     ans.mi=min(temp1.mi,temp2.mi);
    65     return ans;
    66 }
    67 
    68 int main(void)
    69 {
    70     int n,q,i,a,b;
    71     pair ans;
    72     scanf("%d%d",&n,&q);
    73     node *head=buildTree(1,n);
    74     for(i=1; i<=n; i++)
    75     {
    76         scanf("%d",&a);
    77         insert(head,i,a);
    78     }
    79     for(i=1; i<=q; i++)
    80     {
    81         scanf("%d%d",&a,&b);
    82         ans=search(head,a,b);
    83         printf("%d
    ",ans.mx-ans.mi);
    84     }
    85     return 0;
    86 }

    解法二:

    利用数组的形式:3704ms

     1 #include<stdio.h>
     2 #include<stdlib.h>
     3 #include<string.h>
     4 #define N 1000010
     5 #define INF 1000010
     6 #define max(a,b) ((a)>(b)?(a):(b))
     7 #define min(a,b) ((a)>(b)?(b):(a))
     8 
     9 int l[N],r[N],i,n;
    10 typedef struct
    11 {
    12     int mx,mi;
    13 } pair;
    14 pair res[N];
    15 
    16 void BuildTree(int x,int y,int p)
    17 {
    18     l[p]=x;
    19     r[p]=y;
    20     if(x==y)
    21         return;
    22     BuildTree(x,(x+y)>>1,2*p);
    23     BuildTree(((x+y)>>1)+1,y,2*p+1);
    24 }
    25 
    26 void Insert(int num,int p)
    27 {
    28     int mid=(l[p]+r[p])>>1;
    29     res[p].mx=max(res[p].mx,num);
    30     res[p].mi=min(res[p].mi,num);
    31     if(l[p]==r[p])
    32         return;
    33     if(i<=mid)
    34         Insert(num,2*p);
    35     else Insert(num,2*p+1);
    36 }
    37 
    38 pair search(int x,int y,int p)
    39 {
    40     pair a1,a2,ans;
    41     a1.mx=a2.mx=0;
    42     a1.mi=a2.mi=INF;
    43     int mid=(l[p]+r[p])>>1;
    44     if(x<=l[p]&&y>=r[p])
    45         return res[p];
    46     if(x<=mid)
    47     a1=search(x,y,2*p);
    48     if(y>mid)
    49     a2=search(x,y,2*p+1);
    50     ans.mx=max(a1.mx,a2.mx);
    51     ans.mi=min(a1.mi,a2.mi);
    52     return ans;
    53 }
    54 
    55 int main(void)
    56 {
    57     int q,j,x,y;
    58     pair ans;
    59     memset(res,0,sizeof(res));
    60     scanf("%d%d",&n,&q);
    61     BuildTree(1,n,1);
    62     for(i=0; i<N; i++)
    63         res[i].mi=INF;
    64     for(i=1; i<=n; i++)
    65     {
    66         scanf("%d",&j);
    67         Insert(j,1);
    68     }
    69 
    70     for(i=0; i<q; i++)
    71     {
    72         scanf("%d%d",&x,&y);
    73         ans=search(x,y,1);
    74         printf("%d
    ",ans.mx-ans.mi);
    75     }
    76     return 0;
    77 }

     解法三:

    这是利用别人的算法改进而来,所以有时候多借鉴别人的代码,并且可以和自己的想法结合起来,效果还不错.

     1 #include<stdio.h>
     2 #include<string.h>
     3 #include<stdlib.h>
     4 #define N 50010
     5 #define INF 1000010
     6 #define max(a,b) ((a)>(b)?(a):(b))
     7 #define min(a,b) ((a)>(b)?(b):(a))
     8 
     9 typedef struct
    10 {
    11     int l,r;
    12     int mx,mi;
    13 } pair;
    14 pair temp[N*3];
    15 int Max,Min;
    16 
    17 void BuildTree(int x,int y,int p)
    18 {
    19     temp[p].l=x;
    20     temp[p].r=y;
    21     temp[p].mx=0;
    22     temp[p].mi=INF;
    23     if(x==y)
    24         return;
    25     int mid=(x+y)/2;
    26     BuildTree(x,mid,p*2);
    27     BuildTree(mid+1,y,2*p+1);
    28 }
    29 
    30 void Insert(int v,int num,int p)
    31 {
    32     if(temp[v].l==temp[v].r)
    33     {
    34         temp[v].mx=temp[v].mi=num;
    35         return ;
    36     }
    37     int mid=(temp[v].r+temp[v].l)/2;
    38     if(p<=mid)
    39     {
    40         Insert(2*v,num,p);
    41         temp[v].mx=max(temp[v].mx,temp[2*v].mx);
    42         temp[v].mi=min(temp[v].mi,temp[2*v].mi);
    43     }
    44     else
    45     {
    46         Insert(2*v+1,num,p);
    47         temp[v].mx=max(temp[v].mx,temp[2*v+1].mx);
    48         temp[v].mi=min(temp[v].mi,temp[2*v+1].mi);
    49     }
    50 }
    51 
    52 void search(int x,int y,int p)
    53 {
    54     if(temp[p].l==x&&temp[p].r==y)
    55     {
    56         Max=max(Max,temp[p].mx);
    57         Min=min(Min,temp[p].mi);
    58         return;
    59     }
    60     int mid=(temp[p].l+temp[p].r)/2;
    61     if(x>mid)
    62     {
    63         search(x,y,2*p+1);
    64     }
    65     else if(y<=mid)
    66     {
    67         search(x,y,2*p);
    68     }
    69     else
    70     {
    71         search(x,mid,2*p);
    72         search(mid+1,y,2*p+1);
    73     }
    74     return;
    75 }
    76 
    77 int main(void)
    78 {
    79     int n,q,i,x,y;
    80     scanf("%d%d",&n,&q);
    81     BuildTree(1,n,1);
    82     for(i=1;i<=n;i++)
    83     {
    84         scanf("%d",&x);
    85         Insert(1,x,i);
    86     }
    87     for(i=0;i<q;i++)
    88     {
    89         scanf("%d%d",&x,&y);
    90         Max=0;
    91         Min=INF;
    92         search(x,y,1);
    93         printf("%d
    ",Max-Min);
    94     }
    95     return 0;
    96 }
  • 相关阅读:
    angularjs的$on、$emit、$broadcast
    angularjs中的路由介绍详解 ui-route(转)
    ionic入门教程-ionic路由详解(state、route、resolve)(转)
    Cocos Creator 加载使用protobuf第三方库,因为加载顺序报错
    Cocos Creator 计时器错误 cc.Scheduler: Illegal target which doesn't have uuid or instanceId.
    Cocos Creator 构造函数传参警告 Can not instantiate CCClass 'Test' with arguments.
    Cocos Creator 对象池NodePool
    Cocos Creator 坐标系 (convertToWorldSpaceAR、convertToNodeSpaceAR)
    Cocos Creator 常驻节点addPersistRootNode
    Cocos Creator 配合Tiled地图的使用
  • 原文地址:https://www.cnblogs.com/rootial/p/3204185.html
Copyright © 2011-2022 走看看