ACM复习(44)10684 我要摇出一个妹子

Description
微信里面的有一个功能叫摇一摇,听说能摇到妹纸。顿时,众教主们看到都马上拿起手机摇啊摇,希望能摇到一个附近的妹纸@_@。不过由于现在微信摇出来的妹纸的距离
具有不确定性,因此白教主想用更好的办法。就是用程序手机了方圆几十公里的所有有玩微信摇一摇的妹纸的坐标,然后尝试找出离自己最近的一个妹纸,并约之@_@ 但是
由于没看到过妹纸本人,因此想先了解一下,所以想找一个离自己至少有一定距离的妹纸,防止过近。
但由于白教主手头上面的工作很多,他只做了手机妹纸坐标这一步,剩下的想拜托你来完成。希望你能帮助白教主,如果成功,白教主肯定有赏赐的^_^

离白教主最近的点就是所有点中,和白教主自己那个点的两点间距离最小,且大过一定距离的那个妹纸。
如果有很多,那么输出x坐标最小的,如果x坐标一样,则输出x坐标一样的点中y坐标最小的。

注意,为计算方便,这里的两点间坐标使用哈密顿距离。
即dis(< x1,y1>,< x2,y2>) = |x1-x2|+|y1-y2|

输入格式
样例输入:
样例输入有多个,每一个case之间用空行分割
第一行是白教主当前的坐标,两个整数(x,y)
第二行是收集到的妹子的个数n,不大于10000
下面是n个妹子的坐标,每一个一行,两个整数(x,y)
所有坐标的x和y都不超过1000
接下来一个数m(m<=10000),表示有m个距离,每一个数表示想找对应的至少mi距离的妹纸
下面是m个整数,每一个整数表示至少的距离mi (mi不超过1000)

输出格式

样例输出:
对于每一个case
输出有m行
每一行输出一个离白教主坐标最近且大于等于mi的坐标,如果不存在,输出-1

输入样例
0 0
6
1 1
2 2
3 4
4 3
3 3
4 4
5
1 2 3 4 7

输出样例
1 1
1 1
2 2
2 2
3 4

提示
请用
while(scanf(“%d”,&x)>0)

。。。。。。。。

之类的输入来读取多个case


解题思路

建立一个数组记录每一个最小距离应该找哪一个妹子就行,即:

设数组:
rdis[ i ] = t
表示最小距离为 i 时应该寻找第 t 个妹子

#include<stdio.h>
#include<math.h>
int main()
{
    int x, y, dis, n, m, t, j, rdis[20002], rmm[10002][2], rm[10002];
    while(scanf("%d %d", &x, &y) > 0)
    {
        // rdis[k] = -1代表该距离未指定妹子
        for(int i = 0; i < 20002; i ++)
            rdis[i] = -1;
        scanf("%d", &n);
        for(int i = 0; i < n; i ++)
            scanf("%d %d", &rmm[i][0], &rmm[i][1]);
        scanf("%d", &m);
        for(int i = 0; i < m; i ++)
            scanf("%d", &rm[i]);
        // 计算所有妹子的距离并将位置信息存入rdis
        for(int i = 0; i < n; i ++)
        {
            t = fabs(rmm[i][0] - x) + fabs(rmm[i][1] - y);
            if(rdis[t] == -1)
                rdis[t] = i;
            else
            {
                if(rmm[i][0] < rmm[rdis[t]][0])
                    rdis[t] = i;
                else if(rmm[i][0] == rmm[rdis[t]][0])
                {
                    if(rmm[i][1] < rmm[rdis[t]][1])
                        rdis[t] = i;
                }
            }
        }
        for(int i = 0; i < m; i ++)
        {
            t = rm[i];
            for(j = t; j < 20002; j ++)
                if(rdis[j] != -1)
                {
                    printf("%d %d\n", rmm[rdis[j]][0], rmm[rdis[j]][1]);
                    break;
                }
            if(j == 20002)
                printf("-1\n");
        }
    }
    return 0;
}

猜你喜欢

转载自blog.csdn.net/sinat_34200786/article/details/79628310