zoukankan      html  css  js  c++  java
  • vijos 1780 开车旅行

    细节巨多。

    倍增即可。

    #include<iostream>
    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<set>
    #include<cmath>
    #include<cstdlib>
    #define maxv 200500
    #define maxn 100500
    #define eps 1e-7
    #define inf 0x7f7f7f7f7f7f7f7fLL
    using namespace std;
    long long n,m,h[maxn],x,y,aft[maxn][3],anc[maxv][20],dis1[maxv][20],dis2[maxv][20],hashed[maxn],pos[maxn];
    long long ret1=0,ret2=0,ans;
    struct pnt
    {
        long long ret,dot,rets;
    }p[5];
    set <long long> s;
    set <long long> ::iterator it;
    double ans1=inf;
    bool cmp(pnt x,pnt y)
    {
        if (x.ret!=y.ret) return x.ret<y.ret;
        return x.rets>y.rets;
    }
    void divide()
    {
        for (long long i=1;i<=n;i++) hashed[i]=h[i];
        sort(hashed+1,hashed+n+1);
        for (long long i=1;i<=n;i++)
        {
            h[i]=lower_bound(hashed+1,hashed+n+1,h[i])-hashed;
            pos[h[i]]=i;
        }
    }
    long long ask(long long x,long long y)
    {
        ret1=0;ret2=0;
        for (long long e=19;e>=0;e--)
        {
            if ((ret1+ret2+dis1[x][e]+dis2[x][e]<=y) && (anc[x][e]))
            {
                ret1+=dis1[x][e];ret2+=dis2[x][e];
                x=anc[x][e];
            }
        }
    }
    void update(long long x)
    {
        if (!ret1) return;
        if ((double)ret2/ret1<ans1) {ans1=(double)ret2/ret1;ans=x;}
        else if (((double)ret2/ret1-ans1<=eps) && (hashed[h[ans]]<hashed[h[x]])) ans=x;
    }
    int main()
    {
        scanf("%lld",&n);
        for (long long i=1;i<=n;i++) scanf("%lld",&h[i]);
        divide();
        for (long long i=n;i>=1;i--)
        {
            for (long long j=1;j<=4;j++) p[j].dot=p[j].ret=inf;
            it=s.lower_bound(h[i]);
            if (it!=s.end())
            {
                p[3].ret=hashed[h[pos[*it]]];p[3].dot=pos[*it];
                if (++it!=s.end()) {p[4].ret=hashed[h[pos[*it]]];p[4].dot=pos[*it];}
                it--;
            }
            if (it!=s.begin())
            {
                it--;
                p[1].ret=hashed[h[pos[*it]]];p[1].dot=pos[*it];
                if (it!=s.begin()) {it--;p[2].ret=hashed[h[pos[*it]]];p[2].dot=pos[*it];it++;}
            }
            for (int j=1;j<=4;j++)
            {
                if (p[j].ret!=inf)
                {
                    p[j].rets=hashed[h[i]]-p[j].ret;
                    p[j].ret=abs(hashed[h[i]]-p[j].ret);
                }
            }
            sort(p+1,p+5,cmp);
            if (p[1].ret!=inf) aft[i][1]=p[1].dot;
            if (p[2].ret!=inf) aft[i][2]=p[2].dot;
            s.insert(h[i]);
        }
        for (long long i=1;i<=n;i++)
        {
            anc[2*i-1][0]=2*aft[i][1];dis1[2*i-1][0]=abs(hashed[h[aft[i][1]]]-hashed[h[i]]);dis2[2*i-1][0]=0;
            anc[2*i][0]=max(2*aft[i][2]-1,(long long)0);dis1[2*i][0]=0;dis2[2*i][0]=abs(hashed[h[aft[i][2]]]-hashed[h[i]]);
        }
        n*=2;
        for (long long e=1;e<=19;e++)
            for (long long i=1;i<=n;i++)
            {
                anc[i][e]=anc[anc[i][e-1]][e-1];
                dis1[i][e]=dis1[i][e-1]+dis1[anc[i][e-1]][e-1];
                dis2[i][e]=dis2[i][e-1]+dis2[anc[i][e-1]][e-1];
            }
        scanf("%lld",&x);
        for (long long i=2;i<=n;i+=2) 
            {ask(i,x);update(i/2);}
        printf("%d
    ",ans);
        scanf("%lld",&m);
        for (long long i=1;i<=m;i++)
        {
            scanf("%lld%lld",&x,&y);
            ask(2*x,y);
            printf("%lld %lld
    ",ret2,ret1);
        }
        return 0;
    }
  • 相关阅读:
    linux安装maven
    Jenkins 改成中文语言显示
    appium怎么按下系统按键?如按下返回键、home键等等
    Jenkins+TestNG+gitlab+maven持续集成
    问题一:使用AndroidDriver而非原来的AppiumDriver的原因
    appium教程
    问题二:appium 搞定权限弹框的一个小办法
    问题三:Appium 的 UIAutomator2 模式下使用 sendKeys 出现错误
    TestNG执行顺序控制
    idea Mac 快捷键
  • 原文地址:https://www.cnblogs.com/ziliuziliu/p/6062321.html
Copyright © 2011-2022 走看看