#include<stdio.h> #include<string.h> #include<map> #include<vector> #include<math.h> #include<algorithm> using namespace std; #define MS(x,y) memset(x,y,sizeof(x)) #define MP(x,y) make_pair(x,y) const int dy[2][4]={0,1,0,1, 1,0,-1,0}; const int dx[2][4]={1,0,-1,0, 0,1,0,1}; int n,H,W; const int N=1005; vector<pair<int,int> >a[N]; int b[N][N]; void push(int w,int y,int x) { a[w].push_back(MP(y,x)); b[y][x]=w; } void listfill(int y,int x,int w1,int w2) { int size1=w1; int size2=w2; int d=0; while(size1--) { push(w1,y,x); y+=dy[0][d]; x+=dx[0][d]; d=(d+1)%4; } while(size2--) { push(w2,y,x); y+=dy[0][d]; x+=dx[0][d]; d=(d+1)%4; } } void linefill(int y,int x,int w1,int w2) { int size1=w1; int size2=w2; int d=0; while(size1--) { push(w1,y,x); y+=dy[1][d]; x+=dx[1][d]; d=(d+1)%4; } while(size2--) { push(w2,y,x); y+=dy[1][d]; x+=dx[1][d]; d=(d+1)%4; } } //用所以奇数画正方形 void square(int y,int x,int top) { for(int o=top;o>=1;o-=2) { ++y; ++x; int d=o/2; int yy=y+d; int xx=x+d; for(int i=yy;i>=y;i--)push(o,i,x); for(int i=x+1;i<=xx;i++)push(o,y,i); } } //用所有偶数画矩形 void rectangle(int h,int w,int top) { if(h&1) { int u=top; int v=h+h-u; int x=1; while(u>v) { listfill(1,x,u,v); u-=2; v+=2; x+=2; } } else { int u=top; int v=w+w-u; int y=1; while(u>v) { linefill(y,1,u,v); u-=2; v+=2; y+=2; } } } void odd() { H=(n+1)/2; W=n; int mv=n; int h=H; int w=W-(mv+1)/2; square(0,w,mv); rectangle(h,w,n-1); } void even() { H=n/2; W=n+1; int mv=n-1; int h=H; int w=W-(mv+1)/2; square(0,w,mv); rectangle(h,w,n); } void printmap() { for(int i=1;i<=H;i++) { for(int j=1;j<=W;j++)printf("%d ",b[i][j]); puts(""); } } void print() { printf("%d %d\n",H,W); for(int i=1;i<=n;i++) { for(int j=0;j<i;j++)printf("%d %d ",a[i][j].first,a[i][j].second); puts(""); } //printmap(); } int main() { while(~scanf("%d",&n)) { for(int i=1;i<=n;i++)a[i].clear(); if(n&1)odd(); else even(); print(); } return 0; } /* 【trick&&吐槽】 比赛的时候不要太悠闲了,不给自己的压力很多时候造成的恶果是,悲惨地只恰好差一分钟AC TwT 【题意】 给你一个n([1,500]),表示有n条蛇,蛇的身长从1到n,每条蛇所占的格子数也恰好等于其身长。 我们希望把这n条蛇,不交叉不溢出地都放到一个h*w的矩形中。(也就是说h*w=(1+n)*n/2) 并且使得: 对于身长为奇数的蛇(1除外),其扭曲的次数恰好为奇数; 对于身长为偶数的蛇(2除外),其扭曲的次数恰好为偶数。 让你构造出其方案,并按照身长从1~n,依次输出所有蛇。对于每条蛇,从头到尾输出其u偶在位置。 【类型】 构造 【分析】 首先,我们要分析这个矩形的形状,矩形的形状是h*w的话,h和w必定是其面积和的因子。 于是我每次想要枚举出最小的满足这个要求的h,然后再进行构造,然后就踏上了悲惨之路。 一个比较优秀的姿势是什么呢? 就是——既然h*w=(1+n)*n/2,我们就从这个公式入手! 所以,如果n为奇数,那我们就有因子{(1+n)/2和n}; 如果n为偶数,那我们就有因子{n/2和(1+n)}。 然后,我们观察到,不论n为奇数还是偶数,对于所有的奇数,我们都是可以这么安排的—— 1357 3357 5557 7777 我们发现,当n为奇数时,所有的奇数,恰好可以构成一个(n+1)/2的正方形 当n为偶数时,所有的奇数,恰好可以构成一个(n-1+1)/2=n/2的正方形 于是,我们可以剔除这个正方形。 然后,对于n为奇数,目前的矩形就是(n+1)/2 * (n-1)/2 对于n为偶数,目前的矩形就是n/2 * (n+2)/2 然后我们此时剩下的全部都是偶数 对于n%4==1,(n+1)/2 * (n-1)/2 可以用(n-1,2),(n-3,4)这样凑,形成的对数恰好是(n-1)/4对,每对的和恰好是n+1 对于n%4==2,n/2 * (n+2)/2 可以用(n)(n-2,2),(n-4,4)这样凑,形成的对数恰好是(n+2)/4对,每对的和恰好是n 对于n%4==3,(n+1)/2 * (n-1)/2 可以用(n-1)(n-3,2),(n-5,4)这样凑,形成的对数恰好是(n+1)/4对,每对的和恰好是n-1 对于n%4==0,n/2 * (n+2)/2 可以用(n,2)(n-2,4),(n-4,6)这样凑,形成的对数恰好是n/4对,每对的和恰好是(n+2) 而()中的每个数或每一对,能拐就拐,于是就都很容易就在2*d的格子中构造出解。于是就可以AC啦。 这个可以分开写,也可以归纳写,总之我们就可以这样AC啦~啦啦啦啦~ 【时间复杂度&&优化】 O((n+1)*n/2) */