zoukankan      html  css  js  c++  java
  • 蚂蚁运输(二分)

    蚂蚁运输

    题目描述:
    LYK 在观察一些蚂蚁。
    蚂蚁想要积攒一些货物来过冬。积攒货物的方法是这样的。
    对于第 i 只蚂蚁,它要从 li出发,拿起货物,走到 ri处放下货物,需要消耗的时间为|ri-li|。
    而且所有蚂蚁都是可以同时进行的,也就是说,假如有 m 只蚂蚁,那么运输完货物的时间为 max{|ri-li|}。
    LYK 决定帮蚂蚁一把,它发明了空间传输装置。具体地,当蚂蚁走到 X 处时,它可以不耗费任意时间的情况下瞬间到达 Y,或者从 Y 到达 X。也就是说,一个蚂蚁如果使用了空间传输装置,它耗费的时间将会是 min{|li-X|+|ri-Y|,|li-Y|+|ri-X|},当然蚂蚁也可以选择徒步走到目标点。
    由于空间传输装置非常昂贵, LYK 打算只建造这么一台机器。并且 LYK 想让蚂蚁运输完货物的时间尽可能短,你能帮帮它吗?
    输入格式:
    第一行两个数 n,m, n 表示 li,ri 的最大值。
    接下来 m 行,每行两个数 li,ri。
    输出格式:
    一个数表示答案
    输入样例
    5 2
    1 3
    2 4
    输出样例
    1
    数据范围
    对于 20%的数据 n,m<=100。
    对于 40%的数据 n,m<=1000。
    对于 60%的数据 n<=100000, m<=1000。
    对于 80%的数据 n,m<=100000。
    对于 100%的数据 n,m<=1000000, 1<=li,ri<=n( li=ri 时你甚至可以无视这只蚂蚁)。
    样例解释
    令空间传输装置的参数中 X=2, Y=3 或者 X=3, Y=2 都行。
    思路:
    二分答案
    读入时保证li<=ri
    无视掉ri==li的情况
    chaeck(mid)时
    设建的传送站为X_Y
    abs(l-X)+abs(r-Y)<=mid
    则要求
    l-X+r-Y<=mid
    l-X+Y-r<=mid
    X-l+r-Y<=mid
    X-l+Y-r<=mid

    l+r-mid<=X+Y<=l+r+mid
    l-r-mid<=X-Y<=l-r+mid
    只要存在X,Y对于所有的l,r满足上面两条件即可

    #include<iostream>
    #include<cstdio>
    using namespace std;
    const int maxn=1000010;
    const int inf=0x7fffffff;
    int n,m,tot;
    struct node
    {
        int l;
        int r;
    }a[maxn];
    bool can(int mid)
    {
        int l=-inf,r=inf;
        for(int i=1;i<=tot;i++)
        {
            if(a[i].r-a[i].l<=mid) continue;
            l=max(l,a[i].l+a[i].r-mid);
            r=min(r,a[i].l+a[i].r+mid);
        }
        if(l>r) return 0;
        l=-inf,r=inf;
        for(int i=1;i<=tot;i++)
        {
            if(a[i].r-a[i].l<=mid) continue;
            l=max(l,a[i].l-a[i].r-mid);
            r=min(r,a[i].l-a[i].r+mid);
        }
        if(l>r) return 0;
        return 1;
    }
    int main()
    {
        freopen("ant.in","r",stdin);
        freopen("ant.out","w",stdout);
        int x,y;
        scanf("%d%d",&n,&m);
        for(int i=1;i<=m;i++)
        {
            scanf("%d%d",&x,&y);
            if(x==y) continue;
            if(x>y) swap(x,y);
            a[++tot].l=x;
            a[tot].r=y;
        }
        int l=0,r=n,mid,ans;
        while(l<=r)
        {
            mid=(l+r)>>1;
            if(can(mid))
            {
                r=mid-1;
                ans=mid;
            }
            else l=mid+1;
        }
        cout<<ans;
        fclose(stdin);fclose(stdout);
        return 0;
    }
  • 相关阅读:
    三、LIKE和通配符
    二、SQL基本语法
    一、认识SQL
    修改配置文件:my.ini
    SQL——创建表、更改表、删除表
    SQL——更新和删除
    windows下svn更新ubuntu共享目录,主机拒绝的问题。
    Debian/Ubuntu包安装工具APT的使用
    samba无法修正错误,因为您要求某些软件包保持现状,就是它们破坏了软件包间的依赖关系
    虚拟机中的ip局域网中其他机子ping不通
  • 原文地址:https://www.cnblogs.com/cax1165/p/6070893.html
Copyright © 2011-2022 走看看