• hdu-6406-dp+ST表


    Taotao Picks Apples

    Time Limit: 2000/2000 MS (Java/Others)    Memory Limit: 131072/131072 K (Java/Others)
    Total Submission(s): 1446    Accepted Submission(s): 449


    Problem Description
    There is an apple tree in front of Taotao's house. When autumn comes, n apples on the tree ripen, and Taotao will go to pick these apples.

    When Taotao picks apples, Taotao scans these apples from the first one to the last one. If the current apple is the first apple, or it is strictly higher than the previously picked one, then Taotao will pick this apple; otherwise, he will not pick.

    Given the heights of these apples h1,h2,,hn, you are required to answer some independent queries. Each query is two integers p,q, which asks the number of apples Taotao would pick, if the height of the p-th apple were q (instead of hp). Can you answer all these queries?
     
    Input
    The first line of input is a single line of integer T (1T10), the number of test cases.

    Each test case begins with a line of two integers n,m (1n,m105), denoting the number of apples and the number of queries. It is then followed by a single line of n integers h1,h2,,hn (1hi109), denoting the heights of the apples. The next m lines give the queries. Each of these m lines contains two integers p (1pn) and q (1q109), as described in the problem statement.
     
    Output
    For each query, display the answer in a single line.
     
    Sample Input
    1 5 3 1 2 3 4 4 1 5 5 5 2 3
     
    Sample Output
    1 5 3
     
     
      如果能看出将这个序列分成两半之后利用一些预处理依旧能在log时间内得到答案的话就好办了,比赛的时候想了半天最后发现看错题目了,以为每次求一下LIS。。。这个是贪心的上升并非最优的。
      我们提前做个ST表,用于处理区间最大值下标的查询。dp[0][i]表示从第一个元素到第i个元素的步数,dp[1][i]表示从i贪心的往后走的步数,对于每个<p,q> ,分成[1,p],[p,n] , 找到[1,p]之间的最大值下标j ,和[p,n]中大于这个最大值的下标k, 答案就是  dp[0][j]+dp[1][k]。
      
     1 #include <iostream>
     2 #include<cmath>
     3 using namespace std;
     4 int N,a[100100];
     5 int f[100100][20],dp[2][100100];
     6 void init(){
     7     for(int i=1;i<=N;++i)f[i][0]=i;
     8     for(int k=1;(1<<k)<=N;++k){
     9         for(int i=1;i+(1<<k)-1<=N;++i){
    10             if(a[f[i][k-1]]>=a[f[i+(1<<(k-1))][k-1]]) f[i][k]=f[i][k-1];
    11             else f[i][k]=f[i+(1<<(k-1))][k-1];
    12         }
    13     }    
    14 }
    15 int query(int L,int R){
    16     if(R<L)return 0;
    17     int k=0;
    18     while((1<<(k+1))-1<=R-L) k++;
    19     if(a[f[L][k]]>=a[f[R-(1<<k)+1][k]]) return f[L][k];
    20     else return f[R-(1<<k)+1][k];
    21 }
    22 int main() {
    23     int t,n,m,i,p,q;
    24     cin>>t;
    25     while(t--){
    26         scanf("%d%d",&n,&m);
    27         for(i=1;i<=n;++i)scanf("%d",a+i);
    28         N=n,init();
    29         dp[0][1]=1;
    30         int maxn=1;
    31         for(i=2;i<=n;++i){
    32             if(a[i]>a[maxn]){
    33                 dp[0][i]=dp[0][maxn]+1;
    34                 maxn=i;
    35             }
    36             else dp[0][i]=-1;
    37         }
    38 
    39         dp[1][n]=1;
    40         for(i=n-1;i>=1;--i){
    41             int l=i+1,r=n;
    42             while(l<r){
    43                 int mid=l+(r-l)/2;
    44                 if(a[query(l,mid)]>a[i]) r=mid;
    45                 else l=mid+1;
    46             }
    47             dp[1][i]=a[r]>a[i]?dp[1][l]+1:1;
    48         }
    49         while(m--){
    50             scanf("%d%d",&p,&q);
    51             int x=query(1,p-1),xx=a[x],ans=dp[0][x];
    52             if(q>a[x]) xx=q,ans++;
    53             int l=p+1,r=n;
    54             while(l<r){
    55                 int mid=l+(r-l)/2;
    56                 if(a[query(p+1,mid)]>xx)r=mid;
    57                 else l=mid+1;
    58             }
    59             if(a[l]>xx) ans+=dp[1][l];
    60             cout<<ans<<endl;
    61         }
    62     }
    63     return 0;
    64 }
        
     
        
  • 相关阅读:
    c/c++字节序转换(转)
    O_DIRECT与O_SYNC区别(转)
    TCMalloc小记(转)
    内存优化总结:ptmalloc、tcmalloc和jemalloc(转)
    不依赖三方库从图像数据中获取宽高-gif、bmp、png、jepg
    Linux查看物理CPU个数、核数、逻辑CPU个数
    unix环境高级编程-3.10-文件共享(转)
    TF_Server gRPC failed, call return code:8:Received message larger than max (45129801 vs. 4194304)
    google doc上的云转换
    telnet 退出命令
  • 原文地址:https://www.cnblogs.com/zzqc/p/9490772.html
Copyright © 2020-2023  润新知