2012-11-14 79 views
5

我正在尋找一種高性能的方式來裁剪一個二維數組。考慮這個例子:'裁剪'二維數組?

我有一個二維數組,構成一個100x100網格。我只想回到60x60。這裏有一個'a'方法的例子,但是我正在尋找指向這種做法的最高性能的方法。

// Settings 
var gridWidth = 100; 
var gridHeight = 100; 

// Populate Grid 
var grid = []; 

for(var i = 0; i<gridWidth; i++){ 
    grid[i] = []; 
    for(var j = 0; j<gridHeight; j++){ 
     grid[i][j] = 0; 
    } 
} 

// Crop Grid 
var rect = {x:20,y:20,w:60,h:60}; 

var crop = []; 
for(var i = rect.x; i<rect.x+rect.w; i++){ 
    crop[i-rect.x] = []; 
    for(var j = rect.y; j<rect.y+rect.h; j++){ 
     crop[i-rect.x][j-rect.y] = grid[i][j]; 
    } 
} 

不勝感激的任何想法...

約翰

回答

2

試試這個方法:

crop = grid.slice(rect.x, rect.x+rect.w); 
for(var i = 0; i<crop.length; i++){ 
    crop[i] = crop[i].slice(rect.y, rect.y+rect.h); 
} 

注意,陣列的尺寸現在rect.w X rect.h是,所有指數分別由rect.xrect.y負偏移。

+0

你的意思是寫'crop [i] = crop [i] .splice(rect.y,rect.y + rect.h)'?否則,索引只是從數組中刪除... –

+0

@FelixKling燁,謝謝。其實,我只是意識到我應該使用'slice',而不是'splice'。 'splice'返回移除的元素。 –

+0

你還應該提到,這將修改原始數組... –

0

你可以嘗試使用Array#slice[MDN],看看你是否獲得任何性能改進。另外儘量避免不必要的計算:

var yend = rect.y + rect.h; 
var crop = []; 

for(var i = rect.x, j = 0, l = rect.x + rect.w; i < l; i++,j++){ 
    crop[j] = grid[i].slice(rect.y, yend); 
} 

您可以測試是否值得來測試邊緣情況。例如,如果rect.x和/或rect.y0,你不需要原始數組了,你可以設置數組(S)(其中修改它們)的.length

var rect = {x:0,y:0,w:60,h:60}; 

grid.length = rect.w; 

for (var i = 0; i < rect.w; i++) { 
    grid[i].length = rect.h; 
} 
+0

我不確定,但第二個看起來並不像它將元素刪除到所需的y偏移量。 –

+0

Ah darn ...這隻會在'rect.y'爲'0'時才起作用: - /可能會刪除這個。 –

2

如何:

function tab(n, func) { 
    for (var a = [], i = 0; i < n; i++) 
     a.push(func(i)); 
    return a; 
} 

function matrix(w, h, values) { 
    return tab(h, function(y) { 
     return tab(w, function(x) { 
      return values(x, y); 
     }) 
    }) 
} 

grid = matrix(7, 10, function(x, y) { 
    return x + ':' + y; 
}) 

這給了我們:

0:0 1:0 2:0 3:0 4:0 5:0 6:0 
0:1 1:1 2:1 3:1 4:1 5:1 6:1 
0:2 1:2 2:2 3:2 4:2 5:2 6:2 
0:3 1:3 2:3 3:3 4:3 5:3 6:3 
0:4 1:4 2:4 3:4 4:4 5:4 6:4 
0:5 1:5 2:5 3:5 4:5 5:5 6:5 
0:6 1:6 2:6 3:6 4:6 5:6 6:6 
0:7 1:7 2:7 3:7 4:7 5:7 6:7 
0:8 1:8 2:8 3:8 4:8 5:8 6:8 
0:9 1:9 2:9 3:9 4:9 5:9 6:9 

的裁剪功能:

function crop(mat, x, y, w, h) { 
    return mat.slice(y, y + h).map(function(row) { 
     return row.slice(x, x + w) 
    }) 
} 

cropped = crop(grid, 2, 1, 5, 6) 

結果:

2:1 3:1 4:1 5:1 6:1 
2:2 3:2 4:2 5:2 6:2 
2:3 3:3 4:3 5:3 6:3 
2:4 3:4 4:4 5:4 6:4 
2:5 3:5 4:5 5:5 6:5 
2:6 3:6 4:6 5:6 6:6