PAT (Basic Level) Practice (中文) 1050 螺旋矩阵 (25 分) 凌宸1642
PAT (Basic Level) Practice (中文) 1050 螺旋矩阵 (25 分)
题目描述
本题要求将给定的 N 个正整数按非递增的顺序,填入“螺旋矩阵”。所谓“螺旋矩阵”,是指从左上角第 1 个格子开始,按顺时针螺旋方向填充。
要求矩阵的规模为 m 行 n 列,满足条件:m×n 等于 N;m≥n;且 m−n 取所有可能值中的最小值。
输入格式:
输入在第 1 行中给出一个正整数 N,第 2 行给出 N 个待填充的正整数。所有数字不超过 10^4,相邻数字以空格分隔。
输出格式:
输出螺旋矩阵。每行 n 个数字,共 m 行。相邻数字以 1 个空格分隔,行末不得有多余空格。
输入样例:
12
37 76 20 98 76 42 53 95 60 81 58 93
输出样例:
98 95 93
42 37 81
53 20 76
58 60 76
题目要求:
作者 CHEN, Yue
单位 浙江大学
代码长度限制 16 KB
时间限制 400 ms
内存限制 64 MB
解题思路:
// 1、我们需要得到 螺旋矩阵 的行 row 与列 col 的值。
可以算出 n 的所有因子,然后找差值最小的两个因子。// 求出所有因子再计算差值有些复杂。
// 考虑到 相差最小的因子一定在 n 的平方根附近 若 n 是一个平方数,很明显最小差值的因子就是它的平方根
例如: n = 16 时,此时的 row = col = sqrt(n)
// 若 n 不是一个平方数,则从 n 的算术平方根 n0 开始往下枚举,枚举到 n 的一个因子的时候,即可得到符合题意的
// col 和 row 的值
例如: n = 10 时,sqrt(10) = 3 (因为col和row都是整型数据,自动取整) ,
但是 3 不是 10 的因子,所以往下枚举 2 , 2 是 10 的因子, 所以满足要求的 row = 5 ,col = 2 ( row >= col )
// 2、保存输入的 length 为 n 的数组,并从大到小排序
// 这里就是基础的 sort 函数运用了 ,存好数组,要求从大到小排序;手写一个与 sort 函数配合的 cmp 即可。
bool cmp(int a , int b){
return a > b ;
}
sort(array,array + array.length() , cmp) ;
// 我就是不想写 cmp 函数怎么办呢? 简单!
// 从大到小排序,我们知道,sort 函数是默认从小到大排序的,我把从小到大的数组,“倒”过来,不就是从大到小啦
sort(array,array + array.length()) ;
reverse(array,array + array.length()) ;
// 3、准备工作做好了,剩下就是怎么将数组里的数,按照螺旋矩阵的要求,给我螺旋进一个二维数组了。
// 数组中有 n 个数要填入螺旋矩阵,所以结束的标志很容易想到是,记录填入了 x 个数,当 x < n 的时候,说明还要填。
int ans[10010][110] = { 0 } , array[10010] ;
int i = 0 , j = 0 , x = 0 ; // i 和 j 表示此时填的位置。
while( x < n ){
// 按照要求,先是从左往右填,所以是 i 保持不变 j 和 x 每次自增 1
/*
划重点,j < col 容易,因为最多也只有 col 列,为啥还需要 ans[i][j] == 0 呢?
因为,我们知道,如果 ans[i][j] 的值是 0 ,那么此时一定没有被前面某圈的螺旋矩阵填入数据,
反之,则这个位置已经被写入数据了,所以就不能继续此次赋值操作了,因为会覆盖以前的数据。
*/
while( j < col && ans[i][j] == 0)
ans[i][j++] = array[x++] ;
// 将需要的位置 拉回到下一起点。
j -- ;
i ++ ;
// 右边 从上往下填, j 不变, i 和 x 自增
while( i < row && ans[i][j] == 0)
ans[i++][j] = array[x++] ;
// 将需要的位置 拉回到下一起点。
j -- ;
i -- ;
// 下边 从右往左填, i 不变, j 自减 , x 自增
while( i < row && ans[i][j] == 0)
ans[i][j--] = array[x++] ;
// 将需要的位置 拉回到下一起点。
j ++ ;
i -- ;
// 左边 从下往上填, j 不变, i 自减 , x 自增
while( i < row && ans[i][j] == 0)
ans[i--][j] = array[x++] ;
// 将需要的位置 拉回到下一起点。
j ++ ;
i ++ ;
}
// 4、螺旋矩阵的输出,二维矩阵的输出,那就不是问题了
for(int i = 0 ; i < r ; i++){
cout << ans[i][0] ;
for(int j = 1 ; j < c ; j++){
cout<<" "<<ans[i][j] ;
}
cout<<endl ;
}
完整代码:
#include<bits/stdc++.h>
using namespace std ;
int ans[10010][110]={0} , num[100010] ;
int n ;
bool cmp(int a , int b){
return a > b ;
}
int main(){
cin >> n ;
for(int i = 0 ; i < n ; i++){
cin >> num[i] ;
}
sort(num , num + n , cmp) ;
int n0 = sqrt(n) , r = 1 , c , x = 0 ;// r为行,c为列
for(int i = n0 ; i >= 1 ; i--){
if(n % i == 0){
r = i ;
break ;
}
}
c = n / r ;
if(r < c) swap(r , c);
int i = 0 , j = 0 ;
while(x < n){
// 从左往右填
while( j < c && ans[i][j] == 0)
ans[i][j++] = num[x++] ;
j-- ;//调整下一条边的起点
i++ ;
// 右边从上往下填
while( i < r && ans[i][j] == 0)
ans[i++][j] = num[x++] ;
i-- ;//调整下一条边的起点
j-- ;
// 下边从右往左填
while( j >= 0 && ans[i][j] == 0)
ans[i][j--] = num[x++] ;
i-- ;//调整下一条边的起点
j++ ;
//从下往上填
while(i >= 0 && ans[i][j] == 0)
ans[i--][j] = num[x++] ;
i++ ;//调整为下一回合起点
j++ ;
}
for(int i = 0 ; i < r ; i++){
cout << ans[i][0] ;
for(int j = 1 ; j < c ; j++){
cout<<" "<<ans[i][j] ;
}
cout<<endl ;
}
return 0 ;
}
PAT (Basic Level) Practice (中文) 1050 螺旋矩阵 (25 分) 凌宸1642的更多相关文章
- PAT (Advanced Level) Practice 1027 Colors in Mars (20 分) 凌宸1642
PAT (Advanced Level) Practice 1027 Colors in Mars (20 分) 凌宸1642 题目描述: People in Mars represent the c ...
- PAT (Advanced Level) Practice 1019 General Palindromic Number (20 分) 凌宸1642
PAT (Advanced Level) Practice 1019 General Palindromic Number (20 分) 凌宸1642 题目描述: A number that will ...
- PAT (Advanced Level) Practice 1011 World Cup Betting (20 分) 凌宸1642
PAT (Advanced Level) Practice 1011 World Cup Betting (20 分) 凌宸1642 题目描述: With the 2010 FIFA World Cu ...
- PAT (Advanced Level) Practice 1005 Spell It Right (20 分) 凌宸1642
PAT (Advanced Level) Practice 1005 Spell It Right (20 分) 凌宸1642 题目描述: Given a non-negative integer N ...
- PAT (Advanced Level) Practice 1001 A+B Format (20 分) 凌宸1642
PAT (Advanced Level) Practice 1001 A+B Format (20 分) 凌宸1642 题目描述: Calculate a+b and output the sum i ...
- PAT (Basic Level) Practice (中文)1055 集体照 (25 分) 凌宸1642
PAT (Basic Level) Practice (中文)1055 集体照 (25 分) 凌宸1642 题目描述: 拍集体照时队形很重要,这里对给定的 N 个人 K 排的队形设计排队规则如下: 每 ...
- PAT (Basic Level) Practice (中文)1070 结绳 (25 分) 凌宸1642
PAT (Basic Level) Practice (中文)1070 结绳 (25 分) 凌宸1642 题目描述 给定一段一段的绳子,你需要把它们串成一条绳.每次串连的时候,是把两段绳子对折,再如下 ...
- PAT (Basic Level) Practice (中文)1065 单身狗 (25 分) 凌宸1642
PAT (Basic Level) Practice (中文)1065 单身狗 (25 分) 凌宸1642 题目描述: "单身狗"是中文对于单身人士的一种爱称.本题请你从上万人的大 ...
- PAT (Advanced Level) Practice 1006 Sign In and Sign Out (25 分) 凌宸1642
PAT (Advanced Level) Practice 1006 Sign In and Sign Out (25 分) 凌宸1642 题目描述: At the beginning of ever ...
随机推荐
- free online markdown editor
free online markdown editor markdown https://blog.csdn.net/xgqfrms/article/details/50129317 In-brows ...
- d3 & hexagon
d3 & hexagon https://bl.ocks.org/mbostock/5249328 https://bl.ocks.org/vasturiano/e70e14483fe01eb ...
- ng 基础
文档 组件的工作只管用户体验,而不用顾及其它. 它应该提供用于数据绑定的属性和方法,以便作为视图和应用逻辑的中介者 组件应该把诸如从服务器获取数据.验证用户输入或直接往控制台中写日志等工作委托给各种服 ...
- 开发Microsoft Teams选项卡应用安全注意事项
我们都知道,为了方便广大的开发人员快速开发Microsoft Teams选项卡应用,微软提供了一个JS SDK,你可以通过这里 https://docs.microsoft.com/en-us/jav ...
- (转)IP协议详解之子网寻址、子网掩码、构造超网
原文网址:http://www.cnblogs.com/way_testlife/archive/2010/10/05/1844399.html 子网寻址 1. 从两级IP地址到三级IP地址 < ...
- 02.Fancy Indexing
import numpy as np x = np.arange(16) index = [3,5,8] x[index] array([3, 5, 8]) X = x.reshape(4,-1) X ...
- FreeRTOS操作系统最全面使用指南
FreeRTOS操作系统最全面使用指南 1 FreeRTOS操作系统功能 作为一个轻量级的操作系统,FreeRTOS提供的功能包括:任务管理.时间管理.信号量.消息队列.内存管理.记录功能等,可基本满 ...
- DQL:data query language用来查询数据库表中的数据
对查询进行优化,应尽量避免全表扫描,首先应考虑在 where 及 order by 涉及的列上建立索引. 如果没有查询条件,则每次查询所有的行.实际应用中,一般要指定查询的条件.对记录进行过滤. 查询 ...
- 使用Reactor完成类似的Flink的操作
一.背景 Flink在处理流式任务的时候有很大的优势,其中windows等操作符可以很方便的完成聚合任务,但是Flink是一套独立的服务,业务流程中如果想使用需要将数据发到kafka,用Flink处理 ...
- Gc root 定义
常说的GC(Garbage Collector) roots,特指的是垃圾收集器(Garbage Collector)的对象,GC会收集那些不是GC roots且没有被GC roots引用的对象.一个 ...