以螺旋顺序打印二维数组
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了以螺旋顺序打印二维数组相关的知识,希望对你有一定的参考价值。
如何以螺旋顺序打印5×5二维数组?
是否有任何公式,以便我可以按螺旋顺序打印任何大小的数组?
我们的想法是将矩阵视为一系列图层,右上图层和左下图层。为了以螺旋方式打印基质,我们可以从这些基质上剥离层,打印去皮部分并递归调用左侧部分的打印件。当我们没有任何要打印的图层时,递归终止。
输入矩阵:
1 2 3 4
5 6 7 8
9 0 1 2
3 4 5 6
7 8 9 1
剥离右上层后:
1 2 3 4
8
5 6 7 2
9 0 1 6
3 4 5 1
7 8 9
从子矩阵剥离左下图层后:
6 7
5 0 1
9 4 5
3
7 8 9
从子矩阵剥离右上层后:
6 7
1
0 5
4
从子矩阵剥离左下图层后:
0
4
递归终止。
C函数:
// function to print the top-right peel of the matrix and
// recursively call the print bottom-left on the submatrix.
void printTopRight(int a[][COL], int x1, int y1, int x2, int y2) {
int i = 0, j = 0;
// print values in the row.
for(i = x1; i<=x2; i++) {
printf("%d ", a[y1][i]);
}
// print values in the column.
for(j = y1 + 1; j <= y2; j++) {
printf("%d ", a[j][x2]);
}
// see if more layers need to be printed.
if(x2-x1 > 0) {
// if yes recursively call the function to
// print the bottom left of the sub matrix.
printBottomLeft(a, x1, y1 + 1, x2-1, y2);
}
}
// function to print the bottom-left peel of the matrix and
// recursively call the print top-right on the submatrix.
void printBottomLeft(int a[][COL], int x1, int y1, int x2, int y2) {
int i = 0, j = 0;
// print the values in the row in reverse order.
for(i = x2; i>=x1; i--) {
printf("%d ", a[y2][i]);
}
// print the values in the col in reverse order.
for(j = y2 - 1; j >= y1; j--) {
printf("%d ", a[j][x1]);
}
// see if more layers need to be printed.
if(x2-x1 > 0) {
// if yes recursively call the function to
// print the top right of the sub matrix.
printTopRight(a, x1+1, y1, x2, y2-1);
}
}
void printSpiral(int arr[][COL]) {
printTopRight(arr,0,0,COL-1,ROW-1);
printf("
");
}
Two dimensional N*N Matrix is Square matrix
理念:
我们必须在四个不同的方向上穿越,像螺旋一样穿过。一旦螺旋层结束,我们必须遍历矩阵内部。总而言之,我们需要5个循环,4个循环像螺旋一样遍历,1个循环遍历各层。
public void printSpiralForm(int[][] a, int length)
{
for( int i = 0 , j = length-1 ; i < j ; i++ , j-- )
{
for( int k = i ; k < j ; k++ )
{
System.out.print( a[i][k] + " " ) ;
}
for( int k = i ; k < j ; k++ )
{
System.out.print(a[k][j] + " ");
}
for( int k = j ; k > i ; k-- )
{
System.out.print(a[j][k] + " ") ;
}
for( int k = j ; k > i ; k-- )
{
System.out.print( a[k][i] + " " ) ;
}
}
if ( length % 2 == 1 )
{
System.out.println( a[ length/2 ][ length/2 ] ) ;
}
}
保持简单 - >
public class spiralMatrix {
public static void printMatrix(int[][] matrix, int rows, int col)
{
int rowStart=0;
int rowEnd=rows-1;
int colStart=0;
int colEnd=col-1;
while(colStart<=colEnd && rowStart<=rowEnd)
{
for(int i=colStart;i<colEnd;i++)
System.out.println(matrix[rowStart][i]);
for(int i=rowStart;i<rowEnd;i++)
System.out.println(matrix[i][colEnd]);
for(int i=colEnd;i>colStart;i--)
System.out.println(matrix[rowEnd][i]);
for(int i=rowEnd;i>rowStart;i--)
System.out.println(matrix[i][colStart]);
rowStart++;
colEnd--;
rowEnd--;
colStart++;
}
}
public static void main(String[] args){
int[][] array={{1,2,3,4},{5,6,7,8}};
printMatrix(array,2,4);
}
}
这是我的实施:
public static void printMatrix(int matrix[][], int M, int N){
int level = 0;
int min = (M < N) ? M:N;
System.out.println();
while(level <= min/2){
for(int j = level; j < N - level - 1; j++){
System.out.print(matrix[level][j] + " ");
}
for(int i = level; i < M - level - 1; i++) {
System.out.print(matrix[i][N - level - 1] + " ");
}
for(int j = N - level - 1; j > level; j--){
System.out.print(matrix[M - level - 1][j] + " ");
}
for(int i = M - level - 1; i > level; i-- ){
System.out.print(matrix[i][level] + " ");
}
level++;
}
}
int N = Integer.parseInt(args [0]);
// create N-by-N array of integers 1 through N
int[][] a = new int[N][N];
for (int i = 0; i < N; i++)
for (int j = 0; j < N; j++)
a[i][j] = 1 + N*i + j;
// spiral
for (int i = N-1, j = 0; i > 0; i--, j++) {
for (int k = j; k < i; k++) System.out.println(a[j][k]);
for (int k = j; k < i; k++) System.out.println(a[k][i]);
for (int k = i; k > j; k--) System.out.println(a[i][k]);
for (int k = i; k > j; k--) System.out.println(a[k][j]);
}
// special case for middle element if N is odd
if (N % 2 == 1) System.out.println(a[(N-1)/2][(N-1)/2]);
}
}
斜线顶行 - >移调 - >翻转 - >重复。
void slashTransposeFlip(int[][] m){
if( m.length * m[0].length == 1){ //only one element left
System.out.print(m[0][0]);
}else{
//print the top row
for(int a:m[0]){System.out.print(a+" ");}
//slash the top row from the matrix.
int[][] n = Arrays.copyOfRange(m,1,m.length);
int[][] temp = n;
int rows = temp.length;
int columns = temp[0].length;
//invert rows and columns and create new array
n = new int[columns][rows];
//transpose
for(int x=0;x<rows;x++)
for(int y=0;y<columns;y++)
n[y][x] = temp[x][y];
//flipping time
for (int i = 0; i < n.length / 2; i++) {
int[] t = n[i];
n[i] = n[n.length - 1 - i];
n[n.length - 1 - i] = t;
}
//recursively call again the reduced matrix.
slashTransposeFlip(n);
}
}
复杂性:单遍历
O(n)
请让我添加我的单循环答案与复杂性O(n)
。我观察到,在矩阵的左右和左右遍历期间,行 - 主索引中分别增加和减少一个。类似地,对于顶部 - 底部和底部 - 顶部横向,n_cols
增加和减少。因此我为此制定了算法。例如,给定(3x5)矩阵,其中条目为行主要索引,打印输出为:1,2,3,4,5,10,15,14,13,12,11,6,7,8,9
。
------->(+1)
^ 1 2 3 4 5 |
(+n_cols) | 6 7 8 9 10 | (-n_cols)
| 11 12 13 14 15
(-1)<-------
代码解决方案
#include <iostream>
using namespace std;
int main() {
// your code goes here
bool leftToRight=true, topToBottom=false, rightToLeft=false, bottomToTop=false;
int idx=0;
int n_rows = 3;
int n_cols = 5;
int cnt_h = n_cols, cnt_v = n_rows, cnt=0;
int iter=1;
for (int i=0; i <= n_rows*n_cols + (n_rows - 1)*(n_cols - 1)/2; i++){
iter++;
if(leftToRight){
if(cnt >= cnt_h){
cnt_h--; cnt=0;
leftToRight = false; topToBottom = true;
//cout << "Iter: "<< iter << " break_leftToRight"<<endl;
}else{
cnt++;
i以上是关于以螺旋顺序打印二维数组的主要内容,如果未能解决你的问题,请参考以下文章
C 语言数组 ( 验证二维数组内存是线性的 | 打印二维数组 | 以一维数组方式打印二维数组 | 打印二维数组值和地址 )