Hướng dẫn find 3 largest numbers in an array in javascript - tìm 3 số lớn nhất trong một mảng trong javascript

Edit: Everything below is still valid. However, it was clarified to me in a comment that the original question did not ask for indexes, and many of the answers were responding to the preexisting question. Apologies for any curtness in my original post.

Even looking at the original question however, I still disagree with recommending sorting in general for this type of question.

I can't believe how many of these answers are worse than the OP's provided solution. Most are more concise, but either:

  • Don't answer the question. Often only providing the top 3 values, when the question also asks for the indexes of the top 3 values.
  • Suggest "sorting" but without even mentioning performance, side-effects or Big-O notation.

This may be a little too long for SO, but I feel like this is pertinent information.

  1. I need a more optimized version of this javascript code to find the 3 largest values in an array.
  2. I need to get the indexes of the largest numbers.
  3. Are there any other easier methods to solve the problem?

I take [3] to mean "I want the method to be more concise / readable", [2] as "indices to be available in the output directly", and [1] to mean "I want the code to be as efficient as possible".

Starting from [3] as it'd be most useful to people: Your original algorithm is quite efficient, but you're basically duplicating code in each of the 3 loops; the only difference in each loop really is that the index changes. If you just wanted to cut down on the number of characters, you could re-write your algorithm [with a couple minor caveats1] as:

function findLargest3[arry] {
  const max = {
    indices: new Array[0, 0, 0],
    points : new Array[0, 0, 0]
  }
  
  // Inner private function to remove duplicate code
  // Modifies "max" as a side-effect
  function setLargest [idx] {
    const lastMax = max.points[idx - 1] || Number.MAX_VALUE;
    for [let i = 0; i < arry.length; i++] {
      if [arry[i] > max.points[idx] && arry[i] < lastMax] {
        max.points[idx] = arry[i];
        max.indices[idx] = i;
      }
    }
  }
  
  // Get's the 0'th, 1st, and 2nd largest items
  for [let i = 0; i < 3; i++] {
    setLargest[i];
  }
  
  return max;
}

let scoreByPattern = new Array[93, 17, 56, 91, 98, 33, 9, 38, 55, 78, 29, 81, 60];
let max = findLargest3[scoreByPattern];
console.log[scoreByPattern + "/******/" + max.points.join["/"]];

Beyond the addition of the function, the only thing I really had to add was: const lastMax = max.points[idx - 1] || Number.MAX_VALUE;. This was just for the case where idx == 0. As there is no max.points[-1]. We want that second check to always return true, so if max.points[idx - 1] doesn't exist, set it to the highest possible value via ||.

This actually ends up being about 4 times slower than your implementation. That slowness is a result of not directly modifying global state [which is faster but harder to maintain] & including that inner function rather than the code duplication. Replacing the inner function with your original duplicated code & leaving every other change the same ends up being 40% faster to execute, because it avoids the creation & calling of the function entirely; but again is easier to read. It also makes extending findLargest3 to become findLargest5 or findLargestN much simpler.

Additionally, it should be the same Big-O as your original solution [see my answer to 1], unlike the solutions involving

// Outer loop
for [var i = 0; i 

Bài Viết Liên Quan

Chủ Đề