如何递归地螺旋遍历矩阵
how to spirally traverse a matrix recursively - javascript
请看这个JSFiddle: https://jsfiddle.net/hc2jcx26/
我正在尝试螺旋遍历矩阵output
(任何大小),以便它每2秒以螺旋顺序打印每个元素到console.log
:
var output = [[0, 1, 2, 3],
[4, 5, 6, 7]];
我期待这样的输出:
0
1 //after 2 seconds delay
2 //after 2 seconds delay
3 //etc.
7
6
5
4
但是我没有得到这个与上面的代码。输出到处都是,甚至没有正确的元素数量。我使用递归在每次迭代后(通过setTimeout
)在我的循环中添加延迟,但我认为我没有正确设置变量。但是当我看代码时,它对我来说是有意义的。我遗漏了什么?
这是我解决你问题的方法。
迭代版本var matrix1 = [
[1, 2, 3, 4],
[5, 6, 7, 8],
[9, 10, 11, 12],
[13, 14, 15, 16]
], matrix2 = [
[1, 2, 3],
[4, 5, 6],
[7, 8, 9],
[10, 11, 12]
], matrix3 = [
[0, 1, 2, 3],
[4, 5, 6, 7]
], matrix4 = [
[1, 2, 3],
[4, 5, 6],
[7, 8, 9]
];
(function (matrix) {
var i,
nRows = matrix.length,
nCols = matrix[0].length,
rowLimit = nRows - 1,
colLimit = nCols - 1,
rounds = 0,
printedElements = 0,
nElements = nRows * nCols,
timeoutLapse = 2000;
function print(val) {
printedElements += 1;
setTimeout(function () {
console.log(val);
}, printedElements * timeoutLapse);
}
do {
for (i = rounds; i <= colLimit - rounds; i += 1) {// from left to right
print(matrix[rounds][i]);
}
for (i = rounds + 1; i <= rowLimit - rounds; i += 1) {// from top to bottom
print(matrix[i][colLimit - rounds]);
}
for (i = colLimit - rounds - 1; i >= rounds; i -= 1) {// from right to left
print(matrix[rowLimit - rounds][i]);
}
for (i = rowLimit - rounds - 1; i >= rounds + 1; i -= 1) {// from bottom to top
print(matrix[i][rounds]);
}
rounds += 1;
} while (printedElements < nElements);
})(matrix4);
这是小提琴(你必须打开控制台才能看到结果)。
递归版本var matrix1 = [
[1, 2, 3, 4],
[5, 6, 7, 8],
[9, 10, 11, 12],
[13, 14, 15, 16]
], matrix2 = [
[1, 2, 3],
[4, 5, 6],
[7, 8, 9],
[10, 11, 12]
], matrix3 = [
[0, 1, 2, 3],
[4, 5, 6, 7]
], matrix4 = [
[1, 2, 3],
[4, 5, 6],
[7, 8, 9]
];
(function(matrix){
var printedElements = 0,
timeoutLapse = 1000;
function print(val) {
printedElements += 1;
setTimeout(function () {
console.log(val);
}, printedElements * timeoutLapse);
}
function printArray(arr) {
for(var i = 0; i < arr.length; i++) {
print(arr[i]);
}
}
// Recursive algorithm, consumes the matrix.
function printMatrix(matrix, direction) {
var dir = direction % 4,
rowLimit = matrix.length - 1,
i;
if (dir === 0) {// from left to right
printArray(matrix.shift());
} else if (dir === 1) {// from top to bottom
for(i = 0; i <= rowLimit; i++) {
print(matrix[i].pop());
}
} else if (dir === 2) {// from right to left
printArray(matrix.pop().reverse());
} else {// from bottom to top
for(i = rowLimit; i >= 0; i--) {
print(matrix[i].shift());
}
}
if (matrix.length) {// Guard
printMatrix(matrix, direction + 1);
}
}
// Initial call.
printMatrix(matrix, 0);
})(matrix4);
我添加了一些例子来测试它。我只是按照螺旋模式每两秒钟打印出矩阵的元素。
可以看到,递归版本更具有声明性,尽管它完全清空了矩阵。这是小提琴
try
var output = [[0, 1, 2, 3],
[4, 5, 6, 7]];
var columns = output[0].length;
var row;
function spiralOrderRecursive (matrix, rowIndex) {
rowIndex = rowIndex || 0;
if (matrix.length) {
row = rowIndex % 2 ? matrix[0].reverse() : matrix[0];
row.forEach(function (item, index) {
setTimeout(function () {
console.log(item);
}, (rowIndex * columns + index) * 2000);
});
spiralOrderRecursive (matrix.slice(1), ++rowIndex);
}
}
spiralOrderRecursive(output);
也是NON - RECURSIVE
var output = [[0, 1, 2, 3, 5],
[6, 7, 8, 9, 10],
[11, 12, 13, 14, 15],
[16, 17, 18, 19, 20]];;
var columns = output[0].length;
function spiralOrder(output) {
output.forEach(function (row, rowIndex) {
row = rowIndex % 2 ? row.reverse() : row;
row.forEach(function (item, index) {
setTimeout(function () {
console.log(item);
}, (rowIndex * columns + index) * 2000);
});
});
}
spiralOrder(output);
你想做的伪代码
spiral_print(matrix)
{
If the matrix has one row
print the row and go to new line
else if the matrix has two rows
print the first row and go to new line
sleep(2)
print the second row in reverse order and go to new line
else
print the first row and go to new line
sleep(2)
print the second row in reverse order and go to new line
sleep(2)
spiral_print(matrix.slice(2))
}
Using JS
更新:利用@acontell的打印功能
function spiral(matrix) {
if (matrix.length <= 0) {
return
}
for (var i = 0; i < matrix[0].length; i++) {
print(matrix[0][i])
}
//Get last col
for (var i = 1; i < matrix.length; i++) {
print(matrix[i][matrix[0].length - 1])
}
//Get last row
for (var i = matrix[0].length - 2; i >= 0; i--) {
print(matrix[matrix.length-1][i])
}
//Get first column
for (var i = matrix.length - 2; i > 0; i--) {
print(matrix[i][0])
}
matrix = matrix.slice(1, -1)
for (var i = 0; i < matrix.length; i++) {
matrix[i] = matrix[i].slice(1, -1)
}
spiral(matrix)
}
function print(val) {
printedElements += 1;
setTimeout(function () {
console.log(val);
}, printedElements * 2000);
}
var printedElements = 0
matrix = [[1, 2, 3, 4],
[5, 6, 7, 8],
[9, 10, 11, 12],
[13, 14, 15, 16]]
matrix1 = [[1, 2, 3, 4, 31],
[5, 6, 7, 8, 32],
[9, 10, 11, 12, 33],
[13, 14, 15, 16, 34],
[35, 36, 37, 38, 39]]
spiral(matrix1)
使用Python 注意:使用numpy
会容易得多def spiral(matrix):
if len(matrix) <= 0:
return
for v in matrix[0]:
print(v)
last_col = [matrix[i][len(matrix[0]) - 1] for i in range(1,len(matrix))]
for v in last_col:
print(v)
last_row = reversed(matrix[len(matrix)-1][0:-1])
for v in last_row:
print(v)
first_col = [matrix[i][0] for i in range (1, len(matrix) - 1)]
first_col = reversed(first_col)
for v in first_col:
print(v)
matrix = matrix[1:len(matrix) - 1]
matrix = [m[1:len(matrix[0]) - 1] for m in matrix]
spiral(matrix)
matrix = [[1, 2, 3, 4],
[5, 6, 7, 8],
[9, 10, 11, 12],
[13, 14, 15, 16]]
matrix1 = [[1, 2, 3, 4, 31],
[5, 6, 7, 8, 32],
[9, 10, 11, 12, 33],
[13, 14, 15, 16, 34],
[35, 36, 37, 38, 39]]
spiral(matrix1)
UPDATE: With numpy
import numpy as np
def spiral(matrix):
if len(matrix) <= 0:
return
for v in matrix[0]:
print(v)
last_col = matrix[1:, -1]
for v in last_col:
print(v)
last_row = reversed(matrix[-1, :-1])
for v in last_row:
print(v)
first_col = reversed(matrix[1:-1, 0])
for v in first_col:
print(v)
matrix = matrix[1:-1, 1:-1]
spiral(matrix)
matrix = [[1, 2, 3, 4],
[5, 6, 7, 8],
[9, 10, 11, 12],
[13, 14, 15, 16]]
matrix1 = [[1, 2, 3, 4, 31],
[5, 6, 7, 8, 32],
[9, 10, 11, 12, 33],
[13, 14, 15, 16, 34],
[35, 36, 37, 38, 39]]
matrix2 = np.array([[1, 2, 3, 4, 31],
[5, 6, 7, 8, 32],
[9, 10, 11, 12, 33],
[13, 14, 15, 16, 34],
[35, 36, 37, 38, 39]])
spiral(matrix2)
相关文章:
- 循环遍历以数组为值的Javascript对象
- 遍历类元素数组,并在jquery中选择同级元素
- Jquery遍历表元素
- Chrome扩展:遍历不同的页面并收集数据
- 如何遍历包含对象的数组-javascript
- 遍历 JSON 对象并检查 URL 是否以某个值结尾
- 遍历AngularJs中的对象
- JQuery 遍历当前 SELECT 值
- 循环遍历包含另一个表单的表单
- 使用Yadda和Protractor重用步骤定义,遍历所需文件
- 遍历D3中所有数据点之间的所有值
- 自动遍历所有链接的事件
- JS.循环遍历多维数组,以计数元素在每列中的出现次数
- 如何使用 document.querySelectorAll 遍历选定的元素
- 使用Javascript反向遍历XML
- 当知道同一hiearch中至少有一个元素时,遍历到元素.结构使用jquery
- Netsuite Suitelet:在不达到治理限制的情况下,遍历事务行项目的列表加载和提交记录
- 遍历DOM查找字符串有时会正确返回
- 如何使用SnapSVG将SVG作为树结构遍历
- 如何递归地螺旋遍历矩阵