Question

If a user enters 5 numbers, lets say... 4, 4, 7, 7, 4. 4 occurred 3 (most number of) times. So the output should be 4.

How can I do this using JavaScript? Would much appreciate your help. Thanks!

I've tried this so far. It works, but it's too long, looking for something short and simple way.

P.S. This is not my homework!

    var n = parseInt(prompt("How many numbers do you like to enter?", ""));
    var num = new Array();

    for (i = 1; i <= n; i++) {
        num[i] = parseInt(prompt("Enter a number", ""));
        document.write("Entered numbers are: " + num[i] + "<br/>");
    }

    var total = new Array();
    for (i = 1; i <= n; i++) {
        var count = 1;
        for (j = i + 1; j <= n; j++) {
            if (num[i] == num[j]) {
                count++;
            }
            total[i] = count;
        }
    }

    var most = 0;
    for (i = 0; i < n; i++) {
        if (most < total[i]) {
            most = total[i];
        }
        var val = i;
    }
    document.write("<br/>" + num[val] + " is occurred " + most + " times");
Was it helpful?

Solution

Create an array a with a lot of numbers, using array literals:

var a = [1, 2, 3, 4, 4, 5, 1, 2, 3, 1, 2, 1, 1];

Create a plain object o, using object literals.

var o = {},          /* Creates a new object */
    i = 0,           /* Declare variable i, initialise value at 0*/
    m = {m:0,t:null},
    t,               /* Declare variable t */
    len = a.length;  /* Declare variable len, set value to the array's length */

Loop through array a using a for(;;)-loop and increment the counter. The counter is stored in a hashmap on object o.
(o[a[i]] || 0) is needed for the first occurrence of the key: When it's not found, the value 0 is used instead of undefined. See also Short-circuit evaluation: Logical OR.

for ( ; i < len ; i++ ) {
    o[ a[i] ] = ( o[ a[i] ] || 0 ) + 1;
}

Then you have an object o which looks like:

o = {
    "1": 5,
    "2": 3,
    "3": 2,
    "4": 2,
    "5": 1
}

Then loop through o using a for(.. in ..)-loop and find max times presented.
At the bottom of the loop, the conditional ternary .. ? .. : .. operator is used:

for ( i in o ) {
    t = { 
        m: o[i], 
        i: i 
    };
    m = m.m < t.m ? t : m;
}

After this loop m is equal to:

m = { 
    i: "1", 
    m: "5"
};

And the maximum value can be captured using:

o[m];

witch gives you:

5

DEMO

http://jsbin.com/utiqey/

var a = [1, 2, 3, 4, 4, 5, 1, 2, 3, 1, 2, 1, 1]; 

var o = {}, 
    i = 0, 
    m = {m:0,t:null}, 
    t,
    len = a.length; 

for ( ; i < len ; i++ ) { 
    o[ a[i] ] = ( o[ a[i] ] || 0 ) + 1; 
} 


for ( i in o ) { 
    t = { 
        m: o[i], 
        i: i 
    };
    m = m.m < t.m ? t : m;
} 

alert(m.i + " is the highest presented " + m.m + " times"); 

OTHER TIPS

No need to make two passes, the following accumulates the max as it counts:

var g = [4, 4, 7, 7, 4, 5, 6, 7, 8, 6, 5, 2, 2, 2, 3, 4, 5]; //your array

for (var t = {}, maxn = g[0], max = 0, gi, i = g.length; i--;) {
  if (max < (t[gi = g[i]] = (t[gi] || 0) + 1)) {
    max = t[gi];
    maxn = gi;
  }
}

document.write ('The number ' + maxn + ' occurs ' + max + 'times');

Edit

A good solution, but the OP likely needs some explanation and some more suitable variable names. The most commonly occurring value in a set is the mode.

// Use any member of g to seed the mode
var mode = g[0];
// The number of times the current mode has occurred
var count = 0;
// Results object
var t = {};
var i = g.length;
var gi;

// Loop over all the members
while (i--) {

  // Get the value at i
  gi = g[i];

  // Keep track of how many times the value has been found  
  // If the number hasn't occured before, add it with count 1
  // Otherwise, add 1 to its count
  t[gi] = (t[gi] || 0) + 1;

  // Set the mode to the current value if it has occurred 
  // more often than the current mode
  if (count < t[gi]) {
    count = t[gi];
    mode = gi;
  }
}

alert('The mode is ' + mode + ' and occurs ' + count + ' times.');

If there is more than one mode, the one found count times first from the end of the array wins.

http://jsbin.com/ageyol/3/edit

var g = [4, 4, 7, 7, 4, 5, 6, 7, 8, 6, 5, 2, 2, 2, 3, 4, 5]; //your array
var t = {}; // object which contain the numbers as properties.

for (var i = 0; i < g.length; i++)
{
    if (!t[g[i]]) t[g[i]] = 0; //if the property doesnt exists , so create one with counter 0.
    t[g[i]]++; // also - increase the property VALUE.
}

var max = 0;

for (i in t)
{
    if (t[i] > max) max = t[i]; //check if property value is larger then the current MAX val.
    document.write(i + "  " + t[i] + "<br/>");
}
document.write(t[max]);

p.s. if there is more than max - so you should iterate .

Sort the array, then the same values are next to each other so you can just loop though them and look for the longest streak:

arr.sort();

var maxValue, maxCount = 0, cnt = 1, last = arr[0];
for (var i = 1; i <= arr.length; i++) {
  if (i = arr.length || arr[i] != last) {
    if (cnt > maxCount) {
      maxCount = cnt;
      maxValue = last;
    }
    cnt = 1;
    if (i < arr.length) last = arr[i];
  } else {
    cnt++;
  }
}

Just to riff off one of the other answers, once you've formed your object of values you could push the values into an array and use Math.max to get the upperbound. Ordinarily Math.max takes a series of numbers, but if you use .apply it can also accept an array. The same is similar for Math.min.

var o = { 1: 5, 2: 3, 3: 2, 4: 2, 5: 1 };

var out = [];
for (var k in o) {
  out.push(o[k]);
}

var upperbound = Math.max.apply(null, out); // 5
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top