2012-12-22 150 views
1

我有兩個數組。我應該對其中一個(降序或升序)進行正常排序,並根據第一個數組的排序方式對另一個排序。這是因爲第一個數組中的每個元素都與第二個數組上的同一個索引元素有關係,我必須保持這種關係爲真。例如:根據另一個數組的排序索引排序數組

sortThis=[3,1,2]; 
sortAccording=["With 3","With 1","With 2]; 

我找不到任何方式接受來自JavaScript的sort功能指標的變化。

+1

他們必須在單獨的數組? – Joseph

+0

他們是分開的,當我把他們,我必須輸出兩個單獨的陣列。但如果再次合併和分裂它們可以解決問題,那麼它就很好。 – Nogitsune

回答

3

解決方案: 要做到這一點,你必須拉鍊兩個數組中只有一個。這是,因爲你有這個兩陣:

sortThis=[3,1,2]; 
sortAccording=["With 3","With 1","With 2]; 

拉鍊他們,你將有以下陣列:

zipped = [{a: 3, b: "With 3"}, {a: 1, b: "With 1"}, {a: 2, b: "With 2"}]; 

然後,通過一個纔能有排序呢:

zippedAndSorted = [{a: 1, b: "With 1"}, {a: 2, b: "With 2"}, {a: 3, b: "With 3"}]; 

下一步是什麼?

那麼,一旦你有這個數組排序由你想要什麼,你必須與地圖函數來提取他們的價值觀和finnaly你將有你的兩個數組由相同的標準來分類:

的代碼:

// your arrays 
sortThis=[3,1,2]; 
sortAccording=["With 3","With 1","With 2"]; 

// the zip function  
function zip(a,b) { 
    return a.map(function(aa, i){ return { i: aa, j: b[i]};}) 
};    

// ziping and sorting the arrays 
var zipped = zip(sortThis, sortAccording); 
zippedAndSorted = zipped.sort(function(a,b){ return a.i - b.i; }); 

// your two sorted arrays 
sortedThis = zippedAndSorted.map(function(a){ return a.i;}); 
sortedAccording = zippedAndSorted.map(function(a){ return a.j;}); 

你也可以看到它在這裏工作:http://jsfiddle.net/lontivero/cfpcJ/

祝你好運!

+0

在'zip'中使用對象不是一個好主意。用陣列數組會更好 - 這樣可以大大簡化排序和「解壓縮」。 – georg

+0

@ thg435:有什麼區別?數組只是一個具有數字屬性的對象,在這裏的代碼中不會有不同的用法。理論上,你需要一個元組。 – Bergi

+0

@Bergi:不同的是,JavaScript知道如何排序多維數組。 – georg

1

例如:

function zip(a, b) { 
    var i = 0, j = 0, r = []; 
    while(i < a.length && j < b.length) 
     r.push([a[i++], b[j++]]); 
    return r; 
} 

function unzip(r) { 
    var a = [], b = []; 
    for(var i = 0; i < r.length; i++) { 
     a.push(r[i][0]); 
     b.push(r[i][1]); 
    } 
    return [a, b]; 
} 

r = zip(sortAccording, sortThis); 
r.sort(); 
r = unzip(r); 

sortAccording = r[0] 
sortThis = r[1] 

的另一種方法:

result = sortAccording. 
    map(function(elem, pos) { return [elem, pos]}). 
    sort(). 
    map(function(elem) { return sortThis[elem[1]]}) 

更好拉鍊的實施方式並解壓縮(與可變的參數數目都工作):

zip = function() { 
    var args = [].slice.call(arguments, 0); 
    return args[0].map(function(_, i) { 
     return args.map(function(a) { 
      return a[i] 
     }) 
    }) 
} 

unzip = function(a) { 
    return a[0].map(function(_, i) { 
     return a.reduce(function(y, e) { 
      return y.concat(e[i]) 
     }, []) 
    }) 
} 
+0

在你的'zip'函數中,不是'i'總是等於'j'嗎?如果是這樣,爲什麼不省略'j'? – Andomar

+0

@Andomar:很好的電話!這裏是[更好的實現](http://stackoverflow.com/a/10284006/989121) – georg

0

我有一個簡單的解決方案。創建第三個索引數組。只需根據第一個數組的排序對索引數組進行排序即可。

var indexArray = []; 
    for (var i=0; i < sortThis.length; i++) { 
    indexArray[i] = i; 
    } 

    indexArray.sort(function(a, b) { 
    return (sortThis[a] > sortThis[b]) ? 1 : (sortThis[a] === sortThis[b]) ? 0 : -1; 
    }); 

    // Now you have the sorted index ready 
    console.log("The first elements in the arrays are: " + sortThis(indexArray[0]) + " and " + sortAccording(indexArray[0])); 
相關問題