原地旋转矩阵应先转置再水平翻转:转置时仅遍历上三角(j > i),翻转时用std::reverse更安全;非原地实现需注意索引为new_matrixj = matrixi,并正确初始化vector(n, vector(n))。

原地旋转需要先转置再翻转
直接逐元素计算新坐标容易出错,尤其边界处理。最稳妥的方式是分两步:先对矩阵做转置(swap(matrix[i][j], matrix[j][i])),再对每行做水平翻转(reverse(matrix[i].begin(), matrix[i].end()))。这两步都是原地操作,空间复杂度 O(1),且逻辑清晰、不易越界。
注意:转置必须只遍历上三角(即 j > i),否则会 swap 两次又变回去;翻转时用 std::reverse 比手写双指针更安全,避免 ++/-- 错位。
非原地实现要小心内存拷贝顺序
如果允许额外空间(比如返回新二维 vector),常见错误是行列索引写反:new_matrix[j][n-1-i] = matrix[i][j] 才是对的。其中 n 是原矩阵边长,i 为行号,j 为列号。
容易踩的坑:
- 把
n-1-i写成n-i-1—— 虽然数学等价,但可读性差,容易和n-i混淆 - 初始化
new_matrix时行列尺寸颠倒:应为vector<vector>>(n, vector<int>(n))</int></vector>,不是(m, vector<int>(n))</int> - 循环变量范围写成
0 却用 <code> 导致越界
vector> 和 int** 处理方式不同
用 vector<vector>></vector> 时,行数列数都可通过 matrix.size() 和 matrix[0].size() 获取,但必须确保非空;若用 C 风格的 int** matrix,需额外传入 n 参数,且不能依赖 sizeof 算维度。
关键区别:
-
vector版本可直接用swap和reverse,无需手动管理内存 -
int**版本若要原地旋转,必须保证内存是连续按行存储的(如new int[n*n]+ 偏移计算),否则matrix[i][j]可能访问非法地址 - LeetCode 上多数题输入是
vector,别下意识写成 C 风格指针操作
旋转后坐标映射公式别硬记
顺时针 90° 的通用映射是:(i, j) → (j, n-1-i)。这个式子在调试时比“第 i 行变成第 (n-1-i) 列”更可靠,因为后者容易混淆方向。
验证方法很简单:代入四个角点 —— (0,0) 应到 (0,n-1),(0,n-1) 应到 (n-1,n-1),(n-1,n-1) 应到 (n-1,0),(n-1,0) 应到 (0,0)。只要有一个不对,说明公式或循环顺序错了。
真正容易被忽略的是:这个公式只适用于正方形矩阵。矩形数组(m×n)顺时针转 90° 后是 n×m,无法原地完成,必须分配新空间 —— 这点很多人在面试时当场卡住。
C++免费学习笔记(深入):立即使用
在学习笔记中,你将探索 C++ 的入门与实战技巧!











