剑指offer 顺时针打印矩阵
问题描述
输入一个矩阵,按照从外向里以顺时针的顺序依次打印出每一个数字,例如,如果输入如下4 X 4矩阵: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 则依次打印出数字1,2,3,4,8,12,16,15,14,13,9,5,6,7,11,10.
C++代码实现
注意:不是方阵,宽高不一定相等
思路:首先获取每一圈的长宽:n, m。存储开始的顶点,每一圈的顶点分开存储,那么行循环n-2次,列循环m-2次,每条边循环存储后,再按顺序存储顶点,。一圈存储完,使得外圈的宽高都减去2,开始顶点行列坐标加1,这是因为每一圈开始都是从行列值相等的顶点开始的。
class Solution {
public:
vector<int> printMatrix(vector<vector<int> > matrix) {
int m = matrix.size();
int n = matrix[0].size();
int i = -1, j = -1;
vector<int> res;
while(m >= 1 && n >= 1)
{
// 开始顶点坐标
i++;
j++;
// 列和行循环的次数
int num_i = m - 2;
int num_j = n - 2;
// 首先存储开始顶点
res.push_back(matrix[i][j]);
// 存储上边行
if (num_j >= 0)
{
for (int k = 1; k <= num_j; k++)
{
res.push_back(matrix[i][j+k]);
}
res.push_back(matrix[i][j+num_j+1]);
}
// 存储右边列
if (num_i >= 0)
{
for (int k = 1; k <= num_i; k++)
{
res.push_back(matrix[i+k][j+num_j+1]);
}
res.push_back(matrix[i+num_i+1][j+num_j+1]);
}
// 存储下边行和左边列
if (num_i >= 0 && num_j >= 0)
{
for (int k = num_j; k >= 1; k--)
{
res.push_back(matrix[i+num_i+1][j+k]);
}
res.push_back(matrix[i+num_i+1][j]);
for (int k = num_i; k >= 1; k--)
{
res.push_back(matrix[i+k][j]);
}
}
// 改变内层的列行
m = m - 2;
n = n - 2;
}
return res;
}
};
python2代码实现
思路:每次存储每一行,存储后将矩阵转置
# -*- coding:utf-8 -*-
class Solution:
# matrix类型为二维列表,需要返回列表
def printMatrix(self, matrix):
outlist = []
while 1:
# 吃掉第一行
outlist.extend(matrix[0])
# 如果还有其他行,去掉第一行。否则跳出循环
if len(matrix)>1:
matrix = matrix[1::]
else :
break
# 转置,把矩阵立起来
matrix =[ [ row[i] for row in matrix] for i in range(len(matrix[0])-1 , -1 , -1) ]
return outlist
java代码实现
思路:使用四个数值标记每圈的顶点
/**
public class TreeNode {
int val = 0;
TreeNode left = null;
TreeNode right = null;
public TreeNode(int val) {
this.val = val;
}
}
*/
import java.util.ArrayList;
public class Solution {
public ArrayList<Integer> printMatrix(int [][] matrix) {
ArrayList<Integer> result = new ArrayList<>();
if(matrix == null)return result;
int low = 0;
int high = matrix.length-1;
int left = 0;
int right = matrix[0].length-1;
while(low <= high && left <= right)
{
//向右
for(int i=left; i <= right; i++)
result.add(matrix[low][i]);
//向下
for(int i = low+1; i <= high; i++)
result.add(matrix[i][right]);
//向左 有可能出现特殊的情况只有一行,为了避免重复访问
if(low < high){
for(int i= right-1; i >= left; i--)
result.add(matrix[high][i]);
}
//向上 有可能出现特殊的情况只有一列,为了避免重复访问
if(left < right){
for(int i = high-1; i >= low+1; i--)
result.add(matrix[i][left]);
}
low++;
high--;
left++;
right--;
}
return result;
}
}