Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to sort an array of odd numbers in ascending order, but keep even numbers at their position?

I want to sort only odd numbers without moving even numbers. For example, when I write :

sortArray([5, 3, 2, 8, 1, 4])

The expected result is :

[1, 3, 2, 8, 5, 4]

I am new to JavaScript and I came across a challenge on the Internet that has me perplexed. I normally wouldn't post asking for a solution on the Internet, BUT I have tried for hours and I would like to learn this concept in JavaScript.

The challenge states :

You have an array of numbers. Your task is to sort ascending odd numbers but even numbers must be on their places. Zero isn't an odd number and you don't need to move it. If you have an empty array, you need to return it.

Here is my code so far, please take it easy on me I am in the beginning stages of programming.

function sortArray(array) {
  let oddNums = [];
  for(let i = 0; i < array.length; i++) {
    if(array[i] % 2 !== 0) {
      oddNums.push(array[i]);
    }
  }
  oddNums = oddNums.sort((a,b)=> a-b);
  array.concat(oddNums);
  array = array.sort((a,b) => a-b);
  return array;
}
like image 462
user7400006 Avatar asked Mar 22 '18 19:03

user7400006


3 Answers

You could take a helper array for the odd indices and another for the odd numbers, sort them and apply them back on the previously stored indices of the original array.

var array = [5, 3, 2, 8, 1, 4],
    indices = [];

array
    .filter((v, i) => v % 2 && indices.push(i))
    .sort((a, b) => a - b)
    .forEach((v, i) => array[indices[i]] = v);

console.log(array);
like image 76
Nina Scholz Avatar answered Oct 08 '22 13:10

Nina Scholz


Here's a solution using mostly the built-in array methods. Get a list of just the odds, sort it, then map through the original, replacing each item with the first sorted odd if the item is odd, or itself if even:

const array = [5, 3, 2, 8, 1, 4] // to: [1, 3, 2, 8, 5, 4]

function sortOddsOnly(arr) {
    const odds = arr
        .filter(x => x%2)
        .sort((a, b) => a - b);
        
    return arr
        .map(x => x%2 ? odds.shift() : x);
}

console.log(sortOddsOnly(array));
like image 39
CRice Avatar answered Oct 08 '22 13:10

CRice


I have a solution like this.
Build a sorted odd number array 1st, and then fill the rest of even numbers in order:

const arr = [5, 3, 2, 8, 1, 4];

const odd = arr.filter(i => i%2 !== 0).sort();
let i = 0,
  result = [];
arr.forEach(e => {
  if (e%2 === 0) {
    result.push(e)
  } else {
    result.push(odd[i]);
    i++;
  }
});

console.log(result);
like image 4
FisNaN Avatar answered Oct 08 '22 14:10

FisNaN