1. 程式人生 > >Super Mario HDU

Super Mario HDU

  • lower_bound( 1,n,num):從陣列的1位置到n位置二分查詢第一個大於或等於num的數字.
  • 找到返回該數字的地址,不存在則返回end。通過返回的地址減去起始地址begin,得到找到數字在陣列中的下標。
  • upper_bound( 1,n,num):從陣列的1位置到n位置二分查詢第一個大於num的數字,
  • 找到返回該數字的地址,不存在則返回end。通過返回的地址減去起始地址begin,得到找到數字在陣列中的下標。
  • 本題需要用upper_bound來查詢,返回下標後再-1才是小於等於K的數目。 
  • 題意:長度為n的陣列a,m次查詢,每次給定一個區間[l,r]和h。求在區間[l,r]內小於等於h的數的個數。
  • 思路:主席樹對每一個字首建一顆線段樹,用主席樹去維護。線段樹中每一個結點代表一個區間。
  • 我們維護結點資訊sum,sum表示這個a陣列在該區間上的值的個數。這樣,求[l,r]中小於等於h的數的個數,
  • 可以通過查詢第r個版本的線段樹和第l-1個版本的線段樹關於“在區間[l,r]內小於等於h的數的個數”的差值來解決。
  • query需要更改,不是找第K大了,是找小於等於K的數目,所以直接用線段樹維護的區間跟K比較來確定
  • 這段區間裡面的sum有哪些是小於等於K值的sum。
  • #include<bits/stdc++.h>
    using namespace std;
    #define maxn 123456
    int root[maxn],tot,a[maxn],h;
    int n,m,num[maxn],snum,t,l,r;
    struct node
    {
        int l,r,sum;
    } tree[maxn*20];
    int getlow(int x)
    {
        return lower_bound(num+1,num+1+snum,x)-num;
    }
    int getup(int x)
    {
        return upper_bound(num+1,num+1+snum,x)-num-1;
    }
    void build(int &u,int l,int r)
    {
        u=++tot;
        tree[u].sum=0;
        if(l==r)return ;
        int mid=(l+r)/2;
        build(tree[u].l,l,mid);
        build(tree[u].r,mid+1,r);
    }
    void updata(int p,int &u,int l,int r,int k)
    {
        u=++tot;
        tree[u]=tree[p];
        tree[u].sum++;
        if(l==r)return;
        int mid=(l+r)/2;
        if(k<=mid)updata(tree[p].l,tree[u].l,l,mid,k);
        else updata(tree[p].r,tree[u].r,mid+1,r,k);
    }
    int query(int l,int r,int t1,int t2,int k)
    {
        if(l==r)return tree[t2].sum-tree[t1].sum;
        int mid=(l+r)/2;
        if(k<=mid)return query(l,mid,tree[t1].l,tree[t2].l,k);
        else
        {
            int ret=tree[tree[t2].l].sum-tree[tree[t1].l].sum;
            ret+=query(mid+1,r,tree[t1].r,tree[t2].r,k);
            return ret;
        }
    }
    int main()
    {
        scanf("%d",&t);
        for(int cas=1; cas<=t; cas++)
        {
            tot=0;
            scanf("%d%d",&n,&m);
            for(int i=1; i<=n; i++)
            {
                scanf("%d",&a[i]);
                num[i]=a[i];
            }
            sort(num+1,num+1+n);
            snum=unique(num+1,num+1+n)-1-num;
            build(root[0],1,snum);
            for(int i=1; i<=n; i++)
                updata(root[i-1],root[i],1,snum,getlow(a[i]));
            printf("Case %d:\n",cas);
            while(m--)
            {
                scanf("%d%d%d",&l,&r,&h);
                l++,r++;
                int k=getup(h);
                if(k==0)
                    printf("0\n");
                else
                    printf("%d\n",query(1,snum,root[l-1],root[r],k));
            }
        }
        return 0;
    }
    

相關推薦

Super Mario HDU - 4417 (主席樹)

Mario is world-famous plumber. His “burly” figure and amazing jumping ability reminded in our memory. Now the poor princess is in trouble again and Mario

Super Mario HDU

lower_bound( 1,n,num):從陣列的1位置到n位置二分查詢第一個大於或等於num的數字. 找到返回該數字的地址,不存在則返回end。通過返回的地址減去起始地址begin,得到找到數字在陣列中的下標。 upper_bound( 1,n,num):從陣

(樹狀數組+離線查詢)HDU 4417 - Super Mario

blog 數組 string 個數 r++ dex 分塊 每次 class 題意: 給定一個數列,最多10萬次查詢l到r不超過h的數字的個數。 分析: 唉,太菜啦。 在線做法應該比較明顯,區間維護平衡樹,用線段樹套平衡樹,或者分塊套平衡樹,應該都能A,但是沒試

HDU 4417 Super Mario(主席樹)

there mon ref seve pin ans ins Go follow Super Mario Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)T

HDU-4417 Super Mario

type mario output trouble ping case hit include any Super Mario Mario is world-famous plumber. His “burly” figure and amazing jumping abi

HDU - 4417 Super Mario 主席樹

數量 \n make In printf ons bound update ket 題意:   給一個數列$\{ a_i \}$,一些詢問$(l_i,r_i,h_i)$,求$j\in [l_i,r_i] ,a_j<=h_i$的元素數量 題解:   問區間內$<=

hdu 4417 Super Mario

display view main isp case mario using font per 主席樹求區間小於某個數的數的個數模板(靜態) #include <bits/stdc++.h> using namespace std; const int

hdu 4417 Super Mario (主席樹)

代碼 i++ uil 我們 php amp build iostream sort 鏈接:http://acm.hdu.edu.cn/showproblem.php?pid=4417 題意: 給你段長為n的序列,有q個詢問,每次詢問區間[l.r]內有多少個數小於等於k

HDU 4417.Super Mario-無修改區間小於等於H的數的個數-可持久化線段樹

url java ios else string mes clu ber lower Super Mario Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Ot

HDU 4417 Super Mario (樹狀陣列+離線處理)(劃分樹+二分答案)

題意: 給定1--n區間,有q個詢問,詢問l,r,k表示區間[l,r]小於等於k的數的個數 思路: 可以用劃分樹(求區間第k大值)變形一下,來求小於等於k的個數,但是此題直接離線處理詢問高效的多。 首先將1--n區間的值記錄位置,從小到大排序,每個詢問按照k值從小到大排序,

HDU 4417 Super Mario(離線線段樹or樹狀陣列)

Problem Description Mario is world-famous plumber. His “burly” figure and amazing jumping ability reminded in our memory. Now the poor

HDU 4417】Super Mario 【主席樹】

#include<cstdio> #include<iostream> #include<cmath> #include<algorithm> #inc

HDU 4417 Super Mario--離線樹狀陣列、劃分樹、線段樹

題意:詢問區間[l,r]內有幾個數字小於h 思路:對於每次詢問H,L,R,僅需要考慮比H小的hi在L,R範圍內的個數;    為了避免比H大的hi的影響,可以想到對詢問H,和hi進行排序    在詢問H時,僅將比H小的hi插入到樹狀陣列中 #include<

HDU 4417 —— Super Mario(樹狀陣列,離散化,離線處理)

意思比較簡單,就是給N個數(下標從0開始),然後q個詢問,三個引數,L,R,H,詢問序列中在【L,R】這個區間上小於等於H的個數。 挺綜合的一道題目。因為數字最多100000個,數值最多達10^9,所以首先要對數值進行離散化。 像這種區間查詢問題,用S(X,H)表示從0開

【hdu4417】Super Mario——主席樹

== 找到 sca ref cli logs closed event scanf 題目鏈接 題目大意為給定一個長度為n的區間,同時給出m個詢問,每次詢問在區間[l,r]中有多少個數小於或等於k。 同樣考慮用主席樹來維護,每次只需要找到序列b中第一個等於k的數,那麽要求

UVa 10269 Adventure of Super Mario (Floyd + DP + BFS)

highlight tor ble () debug ++ map 必須 ++i 題意:有A個村莊,B個城市,m條邊,從起點到終點,找一條最短路徑。但是,有一種工具可以使人不費力的移動L個長度,但始末點必須是城市或村莊。這種工具有k個,每個只能使用一次,並且在城市內部不可使

hdu4417(Super Mario)—— 二分+劃分樹

Super Mario Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 9714  &n

Reinforcement Learning: Super Mario, AlphaGo and beyond

You might not be able to totally recall the first time you ever played Mario, but just like any other game, you might have started with a clean slate, not

4417 Super Mario —— 線段樹 離線處理

Super Mario Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 9440    Accepted Sub

kali滲透綜合靶機(七)--Super-Mario-Host靶機

kali滲透綜合靶機(七)--Super-Mario-Host靶機 靶機百度雲下載  連結:https://pan.baidu.com/s/13l1FUgJjXArfoTOfcmPsbA 提取碼:a8ox 一、主機發現 1.netdiscover -i eth0 -r 192.168.10.0/24