Minimize sum of array by applying specific operation on x carefully chosen elements This code works, and solves the problem, but doesn't satisfy some time requirements, especially when the 'nums' array can have a length of over 1000. How can this be optimized?
Just reference:
This function does x number of operations on any element in the nums array so that the sum of all elements in the final array is always as small as possible. As a result, you have to perform the operation on the elements with the highest values first.
function minSum(nums, x) {
    if (nums.length === 0) {
        return false;
    }
    function operation(max) { 
        let redcuedMax = Math.floor(max / 10);
        return redcuedMax
    }
    let ops = x;
    while (ops &gt; 0) {
        let max = Math.max(...nums);
        const ofNumber = (element) =&gt; element &gt;= max ;
        let maxIndex = nums.findIndex(ofNumber)
        let operated = operation(max);
        nums[maxIndex] = operated;
        ops--
    }
    return nums.reduce((prev,next) =&gt; prev + next, 0)
}

minSum([400,209,77], 4) //out: 31
minSum([5000,5000,5000,5000,5000,], 4) //out: 7000
You can simplify the code (and maybe accelarate it) by not assigning variables for values that are used once.
spreading the nums array is slow (Math.max), see
also. Math.max with spreading or the faster alternative (Math.max.apply) for a larger array (somewhere between 120.000 - 130.000 elements) will throw a Range Error, so use a loop for it.
reduce is (a lot) slower than a regular loop, so use a
loop to determine the sum
Math.floor can be replaced by a bitwise operator
(it's slightly faster)
Side note: alway use semicolons

The first snippet shows the aforementioned optimizations


const testLongerArray = [...Array(2000)].map((v, i) =&gt; i &amp;&amp; i*10 || 1);
const testVeryLongArray = [...Array(200000)].map((v, i) =&gt; i &amp;&amp; i*10 || 1);
console.log(minSum(testLongerArray, 600)); // out 10812701
console.log(minSum(testVeryLongArray, 1600)); // out 197130527201
console.log(minSum([209,400,77], 4)); //out: 31
console.log(minSum([5000,5000,5000,5000,5000,], 4)); //out: 7000

function maxValue(arr) {
  let max = 0;
  let i = arr.length;
  while (i--) {
    max = arr[i] &gt; max &amp;&amp; arr[i] || max;
  }
  return max;
};

function minSum(nums, x) {
    if (nums.length === 0) {
        return false;
    }
    const start = performance.now();
    
    while (x--) {
        // Note: a loop for max is the fastest
        // and for very large arrays spreading and Math.max.apply
        // will throw, so using the loop here
        const max = maxValue(nums);
        const maxIndex = nums.indexOf(max);
        //               ^ use indexOf
        nums[maxIndex] = (max / 10) | 0;
        //               ^ Math.floor replacement
    }
    
    // replace reduce with a loop
    let len = nums.length;
    let sum = 0;
    
    while (len--) {
      sum += nums[len];
    }

    return `sum: ${sum}, time: ${(performance.now() - start).toFixed(2)} ms`;
}



Now you don't have to iterate through the whole array. If you sort the input array descending, you can take a subset of the first [x length] elements of the sorted input array and perform the operation on the elements of that subset. Adding up the subset elements and the elements of the original sorted array minus its first x elements should give the desired result.
That's worked out in the second snippet. In both snippets the performance is timed, so you can compare both snippets (especially for the longer arrays).


const testLongerArray = [...Array(2000)].map((v, i) =&gt; i &amp;&amp; i * 10 || 1);
const testVeryLongArray = [...Array(200000)].map((v, i) =&gt; i &amp;&amp; i * 10 || 1);
console.log(minSum(testLongerArray, 600)); // out 10812701
console.log(minSum(testVeryLongArray, 1600)); // out 197130527201
console.log(minSum([209, 400, 77], 4)); //out: 31
console.log(minSum([5000, 5000, 5000, 5000, 5000, ], 4)); //out: 7000

function minSum(nums, x) {
  if (nums.length === 0) {
    return false;
  }
  const start = performance.now();
  const operation = v =&gt; (v / 10) | 0;
  nums.sort((a, b) =&gt; b - a);
  let subset = nums.slice(0, x);
  let sum = 0;
  nums = nums.slice(x);

  while (x--) {
    const maxVal = maxValue(subset);
    subset[subset.indexOf(maxVal)] = operation(maxVal);
  }
  nums = nums.concat(subset);
  x = nums.length;
  
  while (x--) {
    sum += nums[x];
  }

  return `sum: ${sum}, time: ${(performance.now() - start).toFixed(2)} ms`;
}

function maxValue(arr) {
  let max = 0;
  let i = arr.length;
  while (i--) {
    max = arr[i] &gt; max &amp;&amp; arr[i] || max;
  }
  return max;
}