Gym - 101667H Rock Paper Scissors 分治

1.题意:给你如下地图的长度和你走的步数,判断你的位置坐标在哪。

Sample Input 1                                        Output for the Sample Input 1 4 10 3 4

Sample Input 2                                        Output for the Sample Input 2 8 19 2 6

2.分析:每一个图片都是由四个上一个图片组成的,都是上方两个为正,下方两个一个往右甩一个往左甩了。于是这里我们就可以分治当前地图了:

(1)对于上方两个小部分分别是上一个地图的(x,y+k)和(x+k,y+k);

(2)对于下方左侧小部分是上一个地图坐标的(y,x);

(3)对于下方右侧小部分是上一个地图坐标的(k+1+k-y  ,  x);

这样一直递归到w1图。。。

3.代码:

#include <iostream>
#include<bits/stdc++.h>
using namespace std;
typedef long long LL;
LL n,k;//地图长度/步数
struct Point{//保存坐标
    LL x,y;
    Point(LL a,LL b):x(a),y(b) {}
};
Point Conquer(LL l,LL step){//分治:当前长度/步数
     if(l==2){//递归终点
        if(step==0)return Point(1,1);//因为用的取余所以判断步数是否为0
        else if(step==1)return Point(1,2);
        else if(step==2)return Point(2,2);
        else if(step==3)return Point(2,1);
     }
     int len = l/2;//地图四分之一
     int all = len*len;//每一部分的步数
     int judge = step/all;//判断当前步数在哪一部分
     if(judge==0){//左下部分
        Point p = Conquer(len,step%all);
        Point another(p.y,p.x);
        return another;
     }
     else if(judge==1){//左上部分
        Point p = Conquer(len,step%all);
        Point another(p.x,p.y+len);
        return another;
     }
     else if(judge==2){//右上部分
        Point p = Conquer(len,step%all);
        Point another(p.x+len,p.y+len);
        return another;
     }
     else if(judge==3){//右下部分
        Point p = Conquer(len,step%all);
        int px = p.y;
        int py = p.x;
        Point another(len+1+(len-px),len-py+1);//坐标是左下部分对称过来
        return another;
     }
}
int main()
{
    scanf("%lld%lld",&n,&k);
    Point p = Conquer(n,k-1);
    printf("%lld %lld\n",p.x,p.y);
    return 0;
}

猜你喜欢

转载自blog.csdn.net/qq_40772692/article/details/82251480