zoukankan      html  css  js  c++  java
  • HDU3577Fast Arrangement(线段树+lazy)

    Problem Description
    Chinese always have the railway tickets problem because of its' huge amount of passangers and stations. Now goverment need you to develop a new tickets query system.
    One train can just take k passangers. And each passanger can just buy one ticket from station a to station b. Each train cannot take more passangers any time. The one who buy the ticket earlier which can be sold will always get the ticket.
     
    Input
    The input contains servel test cases. The first line is the case number. In each test case:
    The first line contains just one number k( 1 ≤ k ≤ 1000 ) and Q( 1 ≤ Q ≤ 100000 )
    The following lines, each line contains two integers a and b, ( 1 ≤ a < b ≤ 1000000 ), indicate a query.
    Huge Input, scanf recommanded.
     
    Output
    For each test case, output three lines:
    Output the case number in the first line.
    If the ith query can be satisfied, output i. i starting from 1. output an blank-space after each number.
    Output a blank line after each test case.
     
    Sample Input
    1
    3 6
    1 6
    1 6
    3 4
    1 5
    1 2
    2 4
     
    Sample Output
    Case 1: 1 2 3 5
     

    即判断哪些人能上车;

    构建线段树的两种情况:

         1,知道范围,且范围不算太大,可以直接构建一个[1,Maxn]的线段树,这样左儿子和右儿子的编号(Lson=now<<1,Rson=now<<1|1)是固定的,不用标记。

         2,不提前构造,累加cnt为新节点标号,加一个root;每个点再ch[2]记录左右儿子的编号。

     lazy的使用,没啥可说的,注意该update就update。

    #include<iostream>
    #include<string>
    #include<algorithm>
    #include<cstdio>
    #include<cstring>
    using namespace std;
    const int maxn=1000005;
    int ans[maxn];
    struct Node
    {
        int l,r,v,lazy;
    }; 
    struct Tree
    {
         Node node[maxn<<2];
         void build(int l,int r,int numb)   
        {
             node[numb].l=l;
             node[numb].r=r;
             node[numb].v=0;
             node[numb].lazy=0;
             if(l==r) return;
             int mid=(l+r)>>1;
             build(l,mid,numb<<1);
             build(mid+1,r,numb<<1|1);
        }
        void PushUp(int numb)               
        {
             node[numb].v=max(node[numb<<1].v,node[numb<<1|1].v);
        }
        void PushDown(int numb)   
        {
             node[numb<<1].lazy+=node[numb].lazy;
             node[numb<<1|1].lazy+=node[numb].lazy;
             node[numb<<1].v+=node[numb].lazy;
             node[numb<<1|1].v+=node[numb].lazy;
             node[numb].lazy=0;             
        }
        void Insert(int l,int r,int numb)   
        {
            if(node[numb].l>=l&&node[numb].r<=r) 
            {
                node[numb].v+=1;
                node[numb].lazy+=1;
                return;
            }
            if(node[numb].lazy) PushDown(numb);
            int mid=(node[numb].r+node[numb].l)>>1;
            if(l>mid) Insert(l,r,numb<<1|1);
            else if(r<=mid) Insert(l,r,numb<<1);
            else{
                Insert(l,mid,numb<<1);
                Insert(mid+1,r,numb<<1|1);
            }
            PushUp(numb);    
       }
        int query(int l,int r,int numb)   
        {
            if(node[numb].l>=l&&node[numb].r<=r){
              return node[numb].v;
            }
            if(node[numb].lazy) PushDown(numb); 
            int mid=(node[numb].r+node[numb].l)>>1;
            if(l>mid) return query(l,r,numb<<1|1);
            else if(r<=mid) return query(l,r,numb<<1);
            else{
               return max(query(l,mid,numb<<1),query(mid+1,r,numb<<1|1)); 
            }
        }
    };
    Tree tree;
    int main()
    {
        int t,Case=1,len=0,k,m,a,b;
        scanf("%d",&t);
        while(t--){
            len=0;
            memset(ans,0,sizeof(ans));
            scanf("%d%d",&k,&m);
            tree.build(1,1000000,1);
            for(int i=0;i<m;i++){
                scanf("%d%d",&a,&b);
                b--;                   
                if(tree.query(a,b,1)<k){
                    ans[len++]=i+1;
                    tree.Insert(a,b,1);
                }
            }
            printf("Case %d:
    ",Case++);
            for(int i=0; i<len; i++)    
                printf("%d ",ans[i]);
            printf("
    
    ");
        }
        return 0;
    }
  • 相关阅读:
    【树状数组套权值线段树】bzoj1901 Zju2112 Dynamic Rankings
    【权值线段树】bzoj3224 Tyvj 1728 普通平衡树
    【转载】【树形DP】【数学期望】Codeforces Round #362 (Div. 2) D.Puzzles
    ReStart
    Good-Bye
    【分块打表】bzoj1662 [Usaco2006 Nov]Round Numbers 圆环数
    【分块打表】bzoj1026 [SCOI2009]windy数
    【分块打表】bzoj3798 特殊的质数
    【分块打表】bzoj3758 数数
    【线段树】bzoj3995 [SDOI2015]道路修建
  • 原文地址:https://www.cnblogs.com/hua-dong/p/7908490.html
Copyright © 2011-2022 走看看