顺时针打印矩阵

题目描述

输入一个矩阵,按照从外向里以顺时针的顺序依次打印出每一个数字,例如,如果输入如下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.

解题思路一

public static ArrayList<Integer> printMatrix(int[][] matrix) {
    if (matrix == null || matrix.length == 0)
        return null; //无法构成矩阵
    ArrayList<Integer> resultList = new ArrayList<Integer>();
    int time = 1;//记录绕圈的次数
    int rowLength = matrix.length;
    int colLength = matrix[0].length;
    while (colLength - time >= time - 1 && rowLength - time >= time - 1) {//仍可以绕圈
        //先横向从左向右遍历
        for (int i = time - 1; i <= colLength - time; i++) {
            resultList.add(matrix[time - 1][i]);
        }
        //第二步,有效最后一列从上到下遍历
        for (int i = time; i <= rowLength - time; i++) {
            resultList.add(matrix[i][colLength - time]);
        }
        //第三步,有效最后一行从右向左遍历
        for (int i = colLength - time - 1; i >= time - 1 && time - 1 != rowLength - time; i--) { // time - 1 != rowLength - time 避免重复输出当前行
            resultList.add(matrix[rowLength - time][i]);
        }
        //第四步,有效最先一列,从下往上遍历
        for (int i = rowLength - time - 1; i >= time && time - 1 != colLength - time; i--) { //time - 1 != colLength - time 避免输出重复列
            resultList.add(matrix[i][time - 1]);
        }
        time++;
    }
    return resultList;
}

解题思路二

想象有四根线在切割,四根线的端点前后链接,确认每次转圈遍历的范围,每转一圈,向中间聚拢,其实跟思路一一致,思路一是以点作为对象考虑,而思路二是以线对对象考虑

public static ArrayList<Integer> printMatrix2(int[][] matrix) {
    ArrayList<Integer> resultList = new ArrayList<Integer>();
    if (matrix == null || matrix.length == 0) {
        return resultList; //无法构成矩阵
    }
    int row = 0; //遍历的当前行坐标
    int rowLength = matrix.length - 1;//行坐标上界
    int col = 0; //遍历的当前列坐标
    int colLength = matrix[0].length - 1; //列坐标上界
    //想象有四根线在切割输出
    while (row <= rowLength && col <= colLength) {//仍可以绕圈
        // 一根线 0度正序输出(从左到右)
        for (int i = col; i <= colLength; i++) {
            resultList.add(matrix[row][i]);
        }
        //第二步,一根线90度正序输出(从上到下)
        for (int i = row + 1; i <= rowLength; i++) {
            resultList.add(matrix[i][colLength]);
        }
        //第三步,一根线180度逆序输出(从右到左)
        for (int i = colLength - 1; i >= col && row != rowLength; i--) { // row != rowLength 避免重复逆序输出当前行
            resultList.add(matrix[rowLength][i]);
        }
        //第四步,一根线270度逆序输出(从下到上)
        for (int i = rowLength - 1; i >= row + 1 && col != colLength; i--) { //time - 1 != colLength - time 避免输出逆序重复列
            resultList.add(matrix[i][col]);
        }
        //缩小四个点的范围
        row++;
        col++;
        rowLength--;
        colLength--;

    }
    return resultList;
}

解题思路三

类似于走迷宫,每次在一个方位走到尽头,然后循环切换下一个方位

public ArrayList<Integer> printMatrix4(int[][] matrix) {
    ArrayList<Integer> resultList = new ArrayList<Integer>();
    if (matrix == null || matrix.length == 0) {
        return resultList; //无法构成矩阵
    }
    //四个方位的坐标变化
    int[] dx = {0, 1, 0, -1};
    int[] dy = {1, 0, -1, 0};
    int x = 0; //当前行坐标
    int y = 0; //当前列坐标
    int rowLength = matrix.length - 1; //行坐标上界
    int colLength = matrix[0].length - 1; //列坐标上界
    int dir = 0; //初始行走方位
    boolean[][] flag = new boolean[rowLength + 1][colLength + 1];//记录每个位置是否走过
    while (x >= 0 && x <= rowLength && y >= 0 && y <= colLength && !flag[x][y]) {
        resultList.add(matrix[x][y]);
        flag[x][y] = true;//已走过
        //把当前方位的格子全部走完
        while (x + dx[dir] >= 0 && x + dx[dir] <= rowLength && y + dy[dir] >= 0 && y + dy[dir] <= colLength && !flag[x + dx[dir]][y + dy[dir]]) {
            x += dx[dir]; //移动到一个方位
            y += dy[dir];
            resultList.add(matrix[x][y]);
            flag[x][y] = true;
        }
        //当前方位走完,换下一方位
        dir = (dir + 1) % 4;
        x += dx[dir];
        y += dy[dir];
    }
    return resultList;

}
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 212,599评论 6 492
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,629评论 3 385
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 158,084评论 0 348
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,708评论 1 284
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 65,813评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,021评论 1 291
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,120评论 3 410
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,866评论 0 268
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,308评论 1 303
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,633评论 2 327
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,768评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,461评论 4 333
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,094评论 3 317
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,850评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,082评论 1 267
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,571评论 2 362
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,666评论 2 350

推荐阅读更多精彩内容

  • 一、题目描述:输入一个矩阵,按照从外向里以顺时针的顺序依次打印出每一个数字,例如,如果输入如下4 X 4矩阵: 1...
    别拿爱情当饭吃阅读 464评论 0 0
  • 原题链接顺时针打印矩阵 题目描述输入一个矩阵,按照从外向里以顺时针的顺序依次打印出每一个数字,例如,如果输入如下4...
    storm_lincoln阅读 349评论 0 0
  • 题干 输入一个矩阵,按照从外向里以顺时针的顺序依次打印出每一个数字。例如,如果输入如下矩阵: 则依次打印出数字 1...
    懒人成长阅读 167评论 0 0
  • 题目描述 输入一个矩阵,按照从外向里以顺时针的顺序依次打印出每一个数字,例如,如果输入如下4 X 4矩阵: 1 2...
    丶沧月阅读 124评论 0 0
  • 题目描述 顺时针打印矩阵 输入一个矩阵,按照从外向里以顺时针的顺序依次打印出每一个数字,例如,如果输入如下4 X ...
    一只可爱的柠檬树阅读 57评论 0 0