HDU 6860 Fluctuation Limit

HDU 6860  Fluctuation Limit

大致思路:

这道题就是对于每一天的变化,都有一个能够变换的区间,只要找到这个区间,就可以解决本题

区间我们通过正反两边扫描找到,正着扫的时候能够满足前面的变化决定后面的变化,反着扫的时候就满足后面的变化决定前面的变化

所以只有同时满足正反两面变化的区间,才是最后成为正确答案的区间

正着扫的时候,这个区间的左边界和右边界分别满足:

 

 反着扫的时候,区间的边界要满足:

 

 

代码如下:

#include<bits/stdc++.h>
#define mem(a) memset(a,0,sizeof(a))
#define forn(i,n) for(int i=0;i<n;++i)
#define for1(i,n) for(int i=1;i<=n;++i)
#define IO std::ios::sync_with_stdio(false); std::cin.tie(0)
#define ll long long
#define inf 0x3f3f3f3f
using namespace std;
const int maxn=1e5+50;
const int mod=1e9+7;

ll l[maxn];
ll r[maxn];
ll up[maxn];
ll down[maxn];

int main()
{
    IO;
    int T;
    cin>>T;
    while(T--)
    {
        ll n,k;
        bool flag=false;
        cin>>n>>k;
        for1(i,n)
        {
            cin>>l[i]>>r[i];
        }
        down[1]=l[1];
        up[1]=r[1];
        for(int i=2; i<=n; ++i)
        {
            up[i]=min(r[i],up[i-1]+k);
            down[i]=max(l[i],down[i-1]-k);
            if(up[i]<down[i])
                flag=true;
        }
        for(int i=n-1; i>=1; --i)
        {
            up[i]=min(up[i],up[i+1]+k);
            down[i]=max(down[i],down[i+1]-k);
            if(up[i]<down[i])
                flag=true;
        }
        if(flag)
            cout<<"NO\n";
        else
        {
            cout<<"YES\n";
            for(int i=1; i<=n; ++i)
                if(i==1)
                    cout<<up[i];
                else
                    cout<<" "<<up[i];
            cout<<"\n";
        }
    }
    return 0;
}

 

posted @ 2020-08-16 11:48  小松QAQ  阅读(215)  评论(0编辑  收藏  举报