如何在javascript中对数组排序?

时间:2022-12-16 15:54:56

I'm not sure if the title of this question is correct or not and also not sure what the appropriate keyword to search on google.

我不确定这个问题的标题是否正确,也不确定在谷歌搜索哪个合适的关键字。

I have an array look like:

我有一个数组看起来像:

var myArray = [1,1,2,2,2,3,4,4,4];

and I want to sort my array into:

我想将我的数组排序为:

var myArray = [1,2,3,4,1,2,4,2,4];

Please in to my expected result. the order is ascending but duplicate value will repeated on last sequence instead of put it together in adjacent keys. So the expected result grouped as 1,2,3,4 1,2,4 and 2,4.

请进入我的预期结果。顺序是升序但重复值将在最后一个序列上重复,而不是将它们放在相邻的键中。因此预期结果分为1,2,3,4 1,2,4和2,4。

Thank you for your help and sorry for my bad English.

谢谢你的帮助,抱歉我的英语不好。

6 个解决方案

#1


3  

This code works. But it may exist a better solution.

这段代码有效。但它可能存在更好的解决方案。

// We assume myArray is already sorted
var myArray = [1,1,2,2,2,3,4,4,4],
    result = [];

while (myArray.length) {
   var value = myArray.shift();

   // Find place
   var index = 0;
   while(result[index] && result[index][result[index].length - 1] == value) index++;

   if(!result[index]) {
      result[index] = [];
   }  

   result[index][result[index].length] = value;
}

result.reduce(function(current, sum) {
  return current.concat(sum);
});

console.log(result) // Display [1, 2, 3, 4, 1, 2, 4, 2, 4]

#2


2  

Here is my method using JQuery and it does not assume the array is already sorted.

这是我使用JQuery的方法,并不假设数组已经排序。

It will iterate through the array and no duplicates to tempResultArray, once finished, it will then add them to the existing result and repeat the process again to find duplicates.

它将遍历数组并且没有重复到tempResultArray,一旦完成,它将把它们添加到现有结果并再次重复该过程以查找重复项。

This is not the most efficient method, but it can be handled by one function and does not require the array to be sorted.

这不是最有效的方法,但它可以由一个函数处理,并且不需要对数组进行排序。

var myArray = [1,1,2,2,2,3,4,4,4],result = [];

while (myArray && myArray.length) {
    myArray = customSort(myArray);
}
console.log(result);

function customSort(myArray){
    var tempResultArray = [], tempMyArray = [];
    $.each(myArray, function(i, el){
        if($.inArray(el, tempResultArray ) === -1){ 
            tempResultArray.push(el);
        }else{
            tempMyArray.push(el); 
        }
   });  
    tempResultArray.sort(function(a, b){return a-b});
    $.merge( result,tempResultArray)
    return tempMyArray;
}

JSFiddle

#3


2  

This proposal features a straight forward approach with focus on array methods.

该提议采用直接的方法,侧重于数组方法。

function sprout(array) {
    return array.reduce(function (r, a) {
        !r.some(function (b) {
            if (b[b.length - 1] < a) {
                b.push(a);
                return true;
            }
        }) && r.push([a]);
        return r;
    }, []).reduce(function (r, a) {
        return r.concat(a);
    });
}

document.write('<pre>' + JSON.stringify(sprout([1, 1, 2, 2, 2, 3, 4, 4, 4]), 0, 4) + '</pre>');
document.write('<pre>' + JSON.stringify(sprout([1, 2, 3, 7, 7, 7]), 0, 4) + '</pre>');
document.write('<pre>' + JSON.stringify(sprout([1, 1, 2, 3, 3, 4, 5, 5, 6, 6, 6, 6, 6, 7]), 0, 4) + '</pre>');

#4


2  

here's another solution:

这是另一个解决方案:

var myArray = [1, 1, 2, 2, 2, 3, 4, 4, 4];


function mySequelArray(arr) {
    var res = arguments[1] || [];
    var nextVal;
    var min = Math.min.apply(null, arr);

    if (res.length > 0) {
        nextVal = arr.filter(function (x) {
            return x > res[res.length - 1]
        }).sort()[0] || min;
    } else {
        nextVal = min;
    }
    res.push(nextVal);
    arr.splice(arr.indexOf(nextVal), 1);

    return (arr.length > 0) ? mySequelArray(arr, res) : res;


}

console.log(mySequelArray(myArray))

fiddle

#5


1  

My best approach will be to split your array into separate arrays for each repeated value, then arrange each separate array and join altogether.

我最好的方法是将数组拆分为每个重复值的单独数组,然后排列每个单独的数组并完全连接。

#6


1  

UPDATED: I wrote a quick code sample that should work if the same number in inputArray is not given more than twice. You could improve it by making it recursive thus creating new arrays for each new number and removing the limitation. Had some free time so i re-wrote a recursive function to sort any given array in sequence groups like you wanted. Works like a charm, inputArray does not need to be sorted and doesn't require any libraries. Jsfiddle here.

更新:我编写了一个快速代码示例,如果inputArray中的相同数字不超过两次,则该代码应该有效。您可以通过递归来改进它,从而为每个新数字创建新数组并消除限制。有一些空闲时间,所以我重新编写了一个递归函数来对序列组中的任何给定数组进行排序,就像你想要的那样。像魅力一样工作,inputArray不需要排序,也不需要任何库。 Jsfiddle在这里。

var inputArray = [3, 4, 1, 2, 3, 1, 2, 4, 1, 2, 5, 1];
var result = sortInSequence(inputArray);
console.log(result); //output: [1, 2, 3, 4, 5, 1, 2, 3, 4, 1, 2, 1]

function sortInSequence(inputArray){
    var inputArraySize = inputArray.length,
        tempArray = [], //holds new array we are populating
        sameValuesArray = [], //holds same values that we will pass as param in recursive call
        rSorted = []; //init sorted array in case we have no same values

    for(var i = inputArraySize; i > 0; i--){
        var value = inputArray.pop();
        tempArray.push(value);

        var counter = 0,
            tempArraySize = tempArray.length;
        for(var j = 0; j < tempArraySize; j++){
            if(tempArray[j] == value){
                counter++;
            }
        }

        if(counter == 2){
            //value found twice, so remove it from tempArray and add it in sameValuesArray
            var sameValue = tempArray.pop();
            sameValuesArray.push(sameValue);
        }
    }

    if(sameValuesArray.length > 0){
        rSorted = sortInSequence(sameValuesArray);
    }

    tempArray.sort();
    return tempArray.concat(rSorted);
}

#1


3  

This code works. But it may exist a better solution.

这段代码有效。但它可能存在更好的解决方案。

// We assume myArray is already sorted
var myArray = [1,1,2,2,2,3,4,4,4],
    result = [];

while (myArray.length) {
   var value = myArray.shift();

   // Find place
   var index = 0;
   while(result[index] && result[index][result[index].length - 1] == value) index++;

   if(!result[index]) {
      result[index] = [];
   }  

   result[index][result[index].length] = value;
}

result.reduce(function(current, sum) {
  return current.concat(sum);
});

console.log(result) // Display [1, 2, 3, 4, 1, 2, 4, 2, 4]

#2


2  

Here is my method using JQuery and it does not assume the array is already sorted.

这是我使用JQuery的方法,并不假设数组已经排序。

It will iterate through the array and no duplicates to tempResultArray, once finished, it will then add them to the existing result and repeat the process again to find duplicates.

它将遍历数组并且没有重复到tempResultArray,一旦完成,它将把它们添加到现有结果并再次重复该过程以查找重复项。

This is not the most efficient method, but it can be handled by one function and does not require the array to be sorted.

这不是最有效的方法,但它可以由一个函数处理,并且不需要对数组进行排序。

var myArray = [1,1,2,2,2,3,4,4,4],result = [];

while (myArray && myArray.length) {
    myArray = customSort(myArray);
}
console.log(result);

function customSort(myArray){
    var tempResultArray = [], tempMyArray = [];
    $.each(myArray, function(i, el){
        if($.inArray(el, tempResultArray ) === -1){ 
            tempResultArray.push(el);
        }else{
            tempMyArray.push(el); 
        }
   });  
    tempResultArray.sort(function(a, b){return a-b});
    $.merge( result,tempResultArray)
    return tempMyArray;
}

JSFiddle

#3


2  

This proposal features a straight forward approach with focus on array methods.

该提议采用直接的方法,侧重于数组方法。

function sprout(array) {
    return array.reduce(function (r, a) {
        !r.some(function (b) {
            if (b[b.length - 1] < a) {
                b.push(a);
                return true;
            }
        }) && r.push([a]);
        return r;
    }, []).reduce(function (r, a) {
        return r.concat(a);
    });
}

document.write('<pre>' + JSON.stringify(sprout([1, 1, 2, 2, 2, 3, 4, 4, 4]), 0, 4) + '</pre>');
document.write('<pre>' + JSON.stringify(sprout([1, 2, 3, 7, 7, 7]), 0, 4) + '</pre>');
document.write('<pre>' + JSON.stringify(sprout([1, 1, 2, 3, 3, 4, 5, 5, 6, 6, 6, 6, 6, 7]), 0, 4) + '</pre>');

#4


2  

here's another solution:

这是另一个解决方案:

var myArray = [1, 1, 2, 2, 2, 3, 4, 4, 4];


function mySequelArray(arr) {
    var res = arguments[1] || [];
    var nextVal;
    var min = Math.min.apply(null, arr);

    if (res.length > 0) {
        nextVal = arr.filter(function (x) {
            return x > res[res.length - 1]
        }).sort()[0] || min;
    } else {
        nextVal = min;
    }
    res.push(nextVal);
    arr.splice(arr.indexOf(nextVal), 1);

    return (arr.length > 0) ? mySequelArray(arr, res) : res;


}

console.log(mySequelArray(myArray))

fiddle

#5


1  

My best approach will be to split your array into separate arrays for each repeated value, then arrange each separate array and join altogether.

我最好的方法是将数组拆分为每个重复值的单独数组,然后排列每个单独的数组并完全连接。

#6


1  

UPDATED: I wrote a quick code sample that should work if the same number in inputArray is not given more than twice. You could improve it by making it recursive thus creating new arrays for each new number and removing the limitation. Had some free time so i re-wrote a recursive function to sort any given array in sequence groups like you wanted. Works like a charm, inputArray does not need to be sorted and doesn't require any libraries. Jsfiddle here.

更新:我编写了一个快速代码示例,如果inputArray中的相同数字不超过两次,则该代码应该有效。您可以通过递归来改进它,从而为每个新数字创建新数组并消除限制。有一些空闲时间,所以我重新编写了一个递归函数来对序列组中的任何给定数组进行排序,就像你想要的那样。像魅力一样工作,inputArray不需要排序,也不需要任何库。 Jsfiddle在这里。

var inputArray = [3, 4, 1, 2, 3, 1, 2, 4, 1, 2, 5, 1];
var result = sortInSequence(inputArray);
console.log(result); //output: [1, 2, 3, 4, 5, 1, 2, 3, 4, 1, 2, 1]

function sortInSequence(inputArray){
    var inputArraySize = inputArray.length,
        tempArray = [], //holds new array we are populating
        sameValuesArray = [], //holds same values that we will pass as param in recursive call
        rSorted = []; //init sorted array in case we have no same values

    for(var i = inputArraySize; i > 0; i--){
        var value = inputArray.pop();
        tempArray.push(value);

        var counter = 0,
            tempArraySize = tempArray.length;
        for(var j = 0; j < tempArraySize; j++){
            if(tempArray[j] == value){
                counter++;
            }
        }

        if(counter == 2){
            //value found twice, so remove it from tempArray and add it in sameValuesArray
            var sameValue = tempArray.pop();
            sameValuesArray.push(sameValue);
        }
    }

    if(sameValuesArray.length > 0){
        rSorted = sortInSequence(sameValuesArray);
    }

    tempArray.sort();
    return tempArray.concat(rSorted);
}