zoukankan      html  css  js  c++  java
  • poj 2265 Bee Maja

    题目的意思很容易理解.就是找两个不同坐标的对应关系.下面的思路转自POJ的论坛

    首先,记由1到2的方向记为2,1到3的方向记为3……1到7的方向记为7,他们分别是:(0,1),(-1,1),(-1,0),(0,-1),(1,-1),(1,0);这些规律不仅对于1的周围六个方向有效,对于所有的点都是有效的。然后记1所在为圈1,2..7为圈1,8..19为圈2……,所以,很容易可以得到第n圈有蜂窝6n个(n>0),对于这个等差数列求和,S[1..n]=3n^2+3n,包括第0圈的1,则S[0..n]=3n^2+3n+1。

    读入数字x,解方程3n^2+3n+1=x,解出来n=[sqrt(12x-3)-3]/6 如果n为整数,则圈数p=n,否则p=trunc(n)+1,又可以通过公式t:=x-3*sqr(p)+3*p-1;求出t(x是第n圈的第t个)。

    可以发现,从上一圈的最后一点,即(p-1,0)走到目的点,首先应在2方向上走1步,再沿(-1,1)走p-1步,其余的5个方向都走p步,此外每走一次,t就要减去相应的值,当t=0时,就可以退出循环,这样就可以很容易得到答案。

    #include<stdio.h>
    #include<math.h>
    int main(){
        double x;
        int n,t,p,x0,y0,i;
        while(scanf("%d",&n)!=EOF){
            x=(sqrt(12*n-3)-3)/6;
            p=(int)x;
            if(3*p*p+3*p+1!=n){
                t=n-(3*p*p+3*p+1);
                p++;
                x0=p-1;
                y0=0;
                while(t){
                    t--;
                    y0++;
                    for(i=1;i<=p-1&&t;i++,t--)x0--,y0++;
                    for(i=1;i<=p&&t;i++,t--)x0--;
                    for(i=1;i<=p&&t;i++,t--)y0--;
                    for(i=1;i<=p&&t;i++,t--)x0++,y0--;
                    for(i=1;i<=p&&t;i++,t--)x0++;
                    for(i=1;i<=p&&t;i++,t--)y0++;
                }
                printf("%d %d
    ",x0,y0);
            }
            else
                printf("%d 0
    ",p);
        }
        return 0;
    }
    View Code

     下面是另外一种解法,其实都差不多的!!!

    #include<iostream>
    #include<stdio.h>
    #include<algorithm>
    #include<iomanip>
    #include<cmath>
    #include<cstring>
    #include<vector>
    #define ll __int64
    #define pi acos(-1.0)
    #define MAX 50000
    using namespace std;
    struct dir
    {
        int x,y;
        dir(){}
        dir(int a,int b){
            x=a;
            y=b;
        }
        dir operator+(dir A){
            return dir(A.x+x,A.y+y);
        }
    }an[6],p;
    int main(){
        int i,j,n,k,x,y,m;
        an[0]=dir(-1,1);an[1]=dir(-1,0);an[2]=dir(0,-1);
        an[3]=dir(1,-1);an[4]=dir(1,0);an[5]=dir(0,1);
        while(cin>>n){
            k=((sqrt(12.0*n-3.0)-3.0)/6.0);
            if(3*k*(k+1)+1!=n) k++;
            p.x=k;p.y=0;
            m=0;
            if(k>0) m=6*k-((3*k*(k+1)+1)-n);
            i=0;
            while(m){
                for(j=0;j<k;j++){
                    p=p+an[i];
                    m--;
                    if(m==0)
                        break;
                }
                i++;
            }
            cout<<p.x<<' '<<p.y<<endl;
        }
        return 0;
    }
    View Code
  • 相关阅读:
    《人月神话》阅读笔记3
    第十五周总结
    《人月神话》阅读笔记2
    对正在使用的输入法评价
    课堂练习(找水王问题)
    第二阶段冲刺第十天
    第二阶段冲刺第九天
    第二阶段冲刺第八天
    第二阶段冲刺第七天
    openwrt U盘启动
  • 原文地址:https://www.cnblogs.com/xin-hua/p/3237096.html
Copyright © 2011-2022 走看看