LeetCode 59.「螺旋矩阵」

问题描述

螺旋矩阵是一道经典的数组操作题目。给定一个正整数n,生成一个包含1到n²所有元素的n×n螺旋矩阵。所谓螺旋矩阵,就是按照顺时针螺旋顺序,从外向内依次填入数字1到n²。

例如,当n=3时,生成的螺旋矩阵为:

复制代码
1 2 3
8 9 4
7 6 5

题目链接

leetcode.cn/problems/sp...

解题思路

解决螺旋矩阵问题的关键在于模拟螺旋填充的过程。我们可以将整个填充过程看作是一层一层向内的循环过程,每一层都是按照"右→下→左→上"的顺序填充数字。

具体步骤如下:

  1. 定义起始位置坐标(startX, startY),初始值为(0, 0)
  2. 定义偏移量offset,用于控制每条边的遍历长度
  3. 定义计数器count,从1开始,表示当前要填入的数字
  4. 创建一个n×n的二维数组res,用于存储结果
  5. 计算需要循环的圈数loop,为n/2(向下取整)
  6. 按照"右→下→左→上"的顺序填充数字
  7. 每完成一圈后,更新起始位置和偏移量
  8. 如果n为奇数,最后需要单独处理矩阵中心的元素

代码实现

javascript 复制代码
var generateMatrix = function (n) {
    let startX = 0;            // 起始行坐标
    let startY = 0;            // 起始列坐标
    let offset = 1;            // 每圈遍历的长度减少量
    let count = 1;             // 当前填入的数字
    let res = new Array(n).fill(0).map(() => new Array(n).fill(0));  // 创建n×n的二维数组

    let loop = Math.floor(n / 2);  // 需要循环的圈数
    while (loop--) {
        let i = startX, j = startY;  // 当前位置

        // 上边:从左到右
        for (; j < n - offset; j++) {
            res[i][j] = count++;
        }
        // 右边:从上到下
        for (; i < n - offset; i++) {
            res[i][j] = count++;
        }
        // 下边:从右到左
        for (; j > startY; j--) {
            res[i][j] = count++;
        }
        // 左边:从下到上
        for (; i > startX; i--) {
            res[i][j] = count++;
        }

        // 更新起始位置
        startX++;
        startY++;
        // 更新偏移量
        offset += 1;
    }

    // 如果n为奇数,单独处理矩阵中心的元素
    if (n % 2 == 1) {
        let mid = Math.floor(n / 2);
        res[mid][mid] = count;
    }
    
    return res;
};

算法分析

  1. 时间复杂度:O(n²),其中n是给定的矩阵大小。我们需要填充n²个元素。
  2. 空间复杂度:O(n²),需要创建一个n×n的二维数组来存储结果。

关键点解析

  1. 边界控制:通过offset变量控制每条边的遍历长度,确保不会重复填充。
  2. 方向转换:使用四个独立的循环分别处理四个方向的填充。
  3. 起始位置更新:每完成一圈后,起始位置向内移动一格。
  4. 中心元素处理:当n为奇数时,矩阵中心的元素需要单独处理。

总结

螺旋矩阵是一道很好的练习数组操作和边界条件处理的题目。解决这类问题的关键在于:

  1. 清晰地定义循环的边界条件
  2. 正确地更新循环变量
  3. 处理特殊情况(如矩阵中心元素)
相关推荐
浪里镖客12 小时前
位姿转换矩阵写法-个人习惯(计算机理解其实是相反的)
线性代数·算法·矩阵
丰锋ff12 小时前
面试问题合集
面试·职场和发展
颜挺锐12 小时前
如何轻松通过性能测试之第四篇:性能测试项目怎么交付?一文讲透九步实施流程(附面试话术 + 实战清单)
面试·职场和发展
敲代码的嘎仔13 小时前
28届后端开发-海康威视日常实习一面(已OC)
java·开发语言·后端·面试·海康威视·实习·大厂
kyriewen14 小时前
面试官让我用 AI 重构一个 8 年陈的 React 组件——他说他不看代码,只看我会不会拆
前端·javascript·面试
黄敬峰15 小时前
一文搞懂 Agent Memory 管理:从临时记忆到长期记忆
面试
Jacky199915 小时前
Electron + Vue 3 桌面打字游戏实战:从 VSCode 扩展到独立应用的架构改造
javascript
小白羊丨15 小时前
如何诊断 Prompt 模板导致的效果下降?
人工智能·算法·prompt
OPEN-F16 小时前
C++11/14新特性精讲:移动语义与智能指针实战
开发语言·c++·算法
柚yuzumi16 小时前
别再猜 this:先看它属于谁,再看它指向谁
前端·javascript