华为OD-D卷螺旋数字矩阵

疫情期间,小明隔离在家,百无聊赖,在纸上写数字玩。他发明了一种写法:

给出数字个数n行数m (0 < n ≤ 999,0 < m ≤ 999),从左上角的1开始,按照顺时针螺旋向内写 方式,依次写出2,3...n,最终形成一个m行矩阵

小明对这个矩阵有些要求

1.每行数字的个数一样多

2.列的数量尽可能少

3.填充数字时优先填充外部

4.数字不够时,使用单个*号占位

输入描述:

两个整数,空格隔开,依次表示n、m

输出描述:

符合要求的唯一矩阵

题目解析:循环遍历,一个大循环(顺时针一次)包括从左到右,从上到下,从右到左,从下到上四次遍历,理清楚每次遍历的起始点和终止点就行。起始点其实就是和上一次遍历的终点紧密相关,终点和循环的次数相关。(额外注意n< m的情况,以及 n % m != 0 的情况)

java 复制代码
import java.util.Scanner;

public class Main {
    public static void main(String[] args) {
//        int n = 9;
//        int m = 4;
        Scanner scanner = new Scanner(System.in);
        int n = scanner.nextInt();
        int m = scanner.nextInt();
        if (n < m) {
            int count = 1;
            for (int i = 0; i < m; i++) {
                if (count <= n) {
                    System.out.println(count++);
                } else {
                    System.out.println("*");
                }
            }
            return;
        }
        int p = (n % m == 0) ? n / m : n / m + 1;
        int[][] nums = new int[m][p];
        int count = 1;
        // 每次循环的开始,第一次是(0,0)坐标,第二次(1,1)...(startX,startY)
        int startX = 0;
        int startY = 0;
        // loop记录已经循环的次数,方便计算终止条件
        int loop = 0;
        // i,j 遍历的当前位置(i,j)
        int i;
        int j;
        int maxLoop = p / 2;
        while (maxLoop > 0) {
            for (j = startY; j < p - loop - 1; j++) {
                if (count <= n) {
                    nums[startX][j] = count++;
                }
            }
            for (i = startX; i < m - loop - 1; i++) {
                if (count <= n) {
                    nums[i][j] = count++;
                }
            }
            for (j = p - loop - 1; j > startY; j--) {
                if (count <= n) {
                    nums[i][j] = count++;
                }
            }
            for (i = m - loop - 1; i > startX; i--) {
                if (count <= n) {
                    nums[i][j] = count++;
                }
            }
            loop++;
            startY++;
            startX++;
            maxLoop--;
        }
        // 不够整除,需要额外遍历一列,注意这一列的终止条件
        if (p % 2 == 1 && count <= n) {
            i = startX;
            for (int k = startX; k <= m - loop - 1; k++) {
                nums[i][k] = count++;
            }
        }
        // 输出结果,注意空格位置
        for (int k = 0; k < m; k++) {
            for (int l = 0; l < p; l++) {
                if (nums[k][l] == 0) {
                    System.out.print("*");
                } else {
                    System.out.print(nums[k][l]);
                }
                if (l != p - 1) {
                    System.out.print(" ");
                }
            }
            System.out.println();
        }
    }
}
相关推荐
阳明山水18 分钟前
校准分位数驱动智能库存决策
人工智能·深度学习·算法·机器学习·架构
别动我齐刘海2 小时前
ROS2 Jazzy + C++ 实战路线——进阶学习3
c++·人工智能·vscode·python·算法·机器学习·机器人
zhangfeng11332 小时前
《从“人工适配“到“智能生成“:KernelSwift 跨国产芯片算子迁移全栈方案解读》 —— 强调范式跃迁和跨硬件属性,适合偏架构分析的写法
人工智能·算法·华为·ai编程·npu
0+1112 小时前
算法 --滑动窗口
c++·算法·leetcode
reikocao2 小时前
大场景下 Hessian 特征值放大与退化检测
算法
hetao17338372 小时前
2026-09-18 hetao1733837 的刷题记录
c++·算法
wuyk5553 小时前
21.计数排序:不用比较的“空间换时间”排序算法
python·算法·排序算法
Rabitebla3 小时前
【Linux系统编程】 指令(二):一条路径是怎么定位到文件的
linux·c++·笔记·学习·算法
库玛西3 小时前
数据结构与算法之美:树、森林与二叉树全解析
c语言·数据结构·笔记·考研·算法·学习方法
木井巳3 小时前
【记忆化搜索】最长递增子序列
java·算法·leetcode·深度优先·剪枝·推荐算法