This time your job is to fill a sequence of N positive integers into a spiral matrix in non-increasing order. A spiral matrix is filled in from the first element at the upper-left corner, then move in a clockwise spiral. The matrix hasm rows and n columns, where m andn satisfy the following: m*n must be equal to N;m>=n; and m-n is the minimum of all the possible values.
Input Specification:
Each input file contains one test case. For each case, the first line gives a positive integer N. Then the next line contains N positive integers to be filled into the spiral matrix. All the numbers are no more than 104. The numbers in a line are separated by spaces.
Output Specification:
For each test case, output the resulting matrix in m lines, each containsn numbers. There must be exactly 1 space between two adjacent numbers, and no extra space at the end of each line.
Sample Input:12 37 76 20 98 76 42 53 95 60 81 58 93Sample Output:
98 95 93 42 37 81 53 20 76 58 60 76
题目大意
给你n个数,将这n个数从大到小螺旋输出。
矩阵(行:row,列:col)的大小满足row*col=n,并且row>=col,并且row-col最小。
解题思路
行列的大小从sqrt(n)开始,小于等于sqrt(n)的第一个数为col,行计算可以用row=n/col。
至于螺旋输出就用一个flag标记控制方向就好。比如到了右边界就要往下走了,或者到了有数的地方也该换向了。
题是个好题,但是数据太水了。10000以下的最大素数为9973,如果用二维矩阵储存理论上最少要9973*9973的size,这肯定超内存了。但是我试了下500*500的size都能过,数据太水了。当然如果按理论来也是能解的,最简单的方法是:因为row和col已经确定了,可以将二维的转换为一维的了(i*row+col),这样只需要10000的size数组就可以了。
下面附上投机的水代码
#include <cstdio>
#include <cmath>
#include <vector>
#include <map>
#include <set>
#include <queue>
#include <stack>
#include <cstdlib>
#include <climits>
#include <cstring>
#include <iostream>
#include <algorithm>
using namespace std;
#define ll long long
const int MAXN = 10000 + 5;
const int MAXM = 100000 + 5;
const int INF = 0x7f7f7f7f;
const int dir[][2] = {0,1,1,0,0,-1,-1,0};
template <class XSD> inline XSD f_min(XSD a, XSD b) { if (a > b) a = b; return a; }
template <class XSD> inline XSD f_max(XSD a, XSD b) { if (a < b) a = b; return a; }
bool cmp(int x, int y){return x>y;}
int n, m;
int mp[500][500];///9973
int a[MAXN];
void Getdata(){
memset(mp, 0, sizeof mp);
for(int i=0; i<n; i++)
scanf("%d", &a[i]);
}
void Solve(){
sort(a, a+n, cmp);
int col=sqrt(n);
while(n%col){col--;}
int row = n/col;
int x=0, y=0, cnt=0;
mp[x][y]=a[cnt++];
int flag=0;
while(cnt < n){
int X = x + dir[flag][0], Y = y + dir[flag][1];
if (X >= row || X < 0 || Y >= col || Y < 0 || mp[X][Y]) flag=(flag+1)%4;
x += dir[flag][0], y += dir[flag][1];
///printf(" %d %d\n", x, y);
mp[x][y] = a[cnt++];
}
for(int i=0; i<row; i++){
for(int j=0; j<col; j++)
printf("%d%c", mp[i][j], j==(col-1)?'\n':' ');
}
}
int main(){
while(~scanf("%d", &n)){
Getdata();
Solve();
}
return 0;
}