程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> C語言 >> C++ >> C++入門知識 >> HDU 4553 約會安排(二維線段樹)

HDU 4553 約會安排(二維線段樹)

編輯:C++入門知識

HDU 4553 約會安排(二維線段樹)


Problem Description   寒假來了,又到了小明和女神們約會的季節。
  小明雖為屌絲級碼農,但非常活躍,女神們常常在小明網上的大段發言後熱情回復“呵呵”,所以,小明的最愛就是和女神們約會。與此同時,也有很多基友找他開黑,由於數量實在過於巨大,怎麼安排時間便成了小明的一大心事。
  我們已知小明一共有T的空閒時間,期間會有很多女神或者基友來找小明。
  作為一個操作系統曾經怒考71分的大神,小明想到了一個算法,即“首次適應算法”,根據操作系統課本的描述,就是找一段最靠前的符合要求的連續空間分配給每個請求,由此小明做出了一個決定:
  當一個基友來找小明時,小明就根據“首次適應算法”來找一段空閒的時間來和基友約好,如果找到,就說“X,let’s fly”(此處,X為開始時間),否則就說“fly with yourself”;
  當女神來找小明時,先使用一次“首次適應算法”,如果沒有找到,小明就冒著木叽叽的風險無視所有屌絲基友的約定,再次使用“無視基友首次適應算法”,兩次只要有一次找到,就說“X,don’t put my gezi”(此處,X為開始時間),否則就說“wait for me”
  當然,我們知道小明不是一個節操負無窮的人,如果和女神約會完,還有剩余時間,他還是會和原來約好的基友去dota的。(舉個例子:小西(屌絲)和小明約好在1~5這個時間單位段內打dota,這時候,女神來和小明預約長度為3的時間段,那麼最終就是1~3小明去和女神約會,搞定後在4~5和小西打dota)
  小明偶爾也會想要學習新知識,此時小明就會把某一個時間區間的所有已經預定的時間全部清空用來學習並且怒吼“I am the hope of chinese chengxuyuan!!”,不過小明一般都是三分鐘熱度,再有人來預定的話,小明就會按耐不住寂寞把學習新知識的時間分配出去。
Input 輸入第一行為CASE,表示有CASE組測試數據;
每組數據以兩個整數T,N開始,T代表總共的時間,N表示預約請求的個數;
接著的N行,每行表示一個女神或者基友的預約,“NS QT”代表一個女神來找小明約一段長為QT的時間,“DS QT”則代表一個屌絲的長為QT的請求,當然也有可能是小明想學知識了,“STUDY!! L R”代表清空L~R區間內的所有請求。

[Technical Specification]
1. 1 <= CASE <= 30
2. 1 <= T, N <= 100000
3. 1 <= QT <= 110000
4. 1 <= L <= R <=T
Output 對於每一個case,第一行先輸出“Case C:”代表是第幾個case,然後N行,每行對應一個請求的結果(參照描述)。
輸出樣本(可復制此處):
“X,let's fly”,”fly with yourself”,”X,don't put my gezi”,”wait for me”,”I am the hope of chinese chengxuyuan!!”

Sample Input
1
5 6
DS 3
NS 2
NS 4
STUDY!! 1 5
DS 4
NS 2

Sample Output
Case 1:
1,let's fly
4,don't put my gezi
wait for me
I am the hope of chinese chengxuyuan!!
1,let's fly
1,don't put my gezi
題意:中文。 線段樹做法:二維,一維表示屌絲,一維表示女神。通過題意我們知道女神對於 屌絲來說有絕對優勢,所以對於屌絲的更新來說只需要考慮自己的第一維,而對 於女神來說更新的時候先在屌絲沒用的時間裡找,如果沒找到就要占用屌絲的時間了。 也就是說無論女神在哪占用的時間,女神和屌絲相應的時間段都要更新, 這道題由於要找端點,所以要區間合並。
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
using namespace std;
#define REPF( i , a , b ) for ( int i = a ; i <= b ; ++ i )
#define REP( i , n ) for ( int i = 0 ; i < n ; ++ i )
#define CLEAR( a , x ) memset ( a , x , sizeof a )
typedef long long LL;
typedef pairpil;
const int maxn=100000+10;
int sum[2][maxn<<2],col[2][maxn<<2];//sum[2][i]屌絲和女神,col=1表示有空位
int lsum[2][maxn<<2],rsum[2][maxn<<2];
int t,n,m;
void pushup(int p,int rs,int s)
{
    lsum[p][rs]=lsum[p][rs<<1];
    rsum[p][rs]=rsum[p][rs<<1|1];
    if(lsum[p][rs<<1]==(s-(s>>1)))  lsum[p][rs]+=lsum[p][rs<<1|1];
    if(rsum[p][rs<<1|1]==(s>>1))  rsum[p][rs]+=rsum[p][rs<<1];
    sum[p][rs]=max(max(sum[p][rs<<1],sum[p][rs<<1|1]),rsum[p][rs<<1]+lsum[p][rs<<1|1]);
}
void pushdown(int p,int rs,int s)
{
    if(col[p][rs]!=-1)
    {
        if(col[p][rs]==1)
        {
            sum[p][rs<<1]=lsum[p][rs<<1]=rsum[p][rs<<1]=(s-(s>>1));
            sum[p][rs<<1|1]=lsum[p][rs<<1|1]=rsum[p][rs<<1|1]=(s>>1);
            col[p][rs<<1]=col[p][rs<<1|1]=1;
            col[p][rs]=-1;
        }
        else
        {
            sum[p][rs<<1]=lsum[p][rs<<1]=rsum[p][rs<<1]=0;
            sum[p][rs<<1|1]=lsum[p][rs<<1|1]=rsum[p][rs<<1|1]=0;
            col[p][rs<<1]=col[p][rs<<1|1]=0;
            col[p][rs]=-1;
        }
    }
}
void build(int p,int l,int r,int rs)
{
    col[p][rs]=-1;
    sum[p][rs]=lsum[p][rs]=rsum[p][rs]=r-l+1;
    if(l==r)
        return ;
    int mid=(l+r)>>1;
    build(p,l,mid,rs<<1);
    build(p,mid+1,r,rs<<1|1);
}
void update(int p,int x,int y,int c,int l,int r,int rs)
{
    if(l>=x&&r<=y)
    {
        col[p][rs]=c;
        if(c) sum[p][rs]=lsum[p][rs]=rsum[p][rs]=r-l+1;
        else  sum[p][rs]=lsum[p][rs]=rsum[p][rs]=0;
        return ;
    }
    pushdown(p,rs,r-l+1);
    int mid=(l+r)>>1;
    if(x<=mid)  update(p,x,y,c,l,mid,rs<<1);
    if(y>mid)  update(p,x,y,c,mid+1,r,rs<<1|1);
    pushup(p,rs,r-l+1);
}
int query(int p,int x,int l,int r,int rs)
{
    if(l==r)
        return l;
    pushdown(p,rs,r-l+1);
    int mid=(l+r)>>1;
    if(sum[p][rs<<1]>=x)  return query(p,x,l,mid,rs<<1);
    else if(rsum[p][rs<<1]+lsum[p][rs<<1|1]>=x)  return mid-rsum[p][rs<<1]+1;
    else  return query(p,x,mid+1,r,rs<<1|1);
    pushup(p,rs,r-l+1);
}

int main()
{
    int x,l,r,ans;
    int cas=1;
    char str[15];
    scanf("%d",&t);
    while(t--)
    {
        scanf("%d%d",&n,&m);
        build(0,1,n,1);
        build(1,1,n,1);
        printf("Case %d:\n",cas++);
        while(m--)
        {
            scanf("%s",str);
            if(str[0]=='D')
            {
                scanf("%d",&x);
                if(sum[0][1]=x)
                {
                    ans=query(0,x,1,n,1);
                    printf("%d,don't put my gezi\n",ans);
                    update(0,ans,ans+x-1,0,1,n,1);
                    update(1,ans,ans+x-1,0,1,n,1);
                }
                else
                {
                    if(sum[1][1]>=x)
                    {
                        ans=query(1,x,1,n,1);
                        printf("%d,don't put my gezi\n",ans);
                        update(0,ans,ans+x-1,0,1,n,1);
                        update(1,ans,ans+x-1,0,1,n,1);
                    }
                    else
                        puts("wait for me");
                }
            }
            else
            {
                scanf("%d%d",&l,&r);
                puts("I am the hope of chinese chengxuyuan!!");
                update(0,l,r,1,1,n,1);
                update(1,l,r,1,1,n,1);
            }
        }
    }
    return 0;
}


  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved