最新消息:Welcome to the puzzle paradise for programmers! Here, a well-designed puzzle awaits you. From code logic puzzles to algorithmic challenges, each level is closely centered on the programmer's expertise and skills. Whether you're a novice programmer or an experienced tech guru, you'll find your own challenges on this site. In the process of solving puzzles, you can not only exercise your thinking skills, but also deepen your understanding and application of programming knowledge. Come to start this puzzle journey full of wisdom and challenges, with many programmers to compete with each other and show your programming wisdom! Translated with DeepL.com (free version)

arrays - Create Frequency Map Using Map - JavaScript - Stack Overflow

matteradmin3PV0评论

Trying to solve this Codwars Kata.

Given an array, find the duplicates in that array, and return a new array of those duplicates. The elements of the returned array should appear in the order when they first appeared as duplicates.

Examples:

[1, 2, 4, 4, 3, 3, 1, 5, 3, '5']  ==>  [4, 3, 1]
[0, 1, 2, 3, 4, 5]                ==>  []

I have:

function duplicates(arr) {

  arr.sort((value, index) => value - index);
  let duplicates = [];
  for (let i = 0; i < arr.length; i++) {
    if (arr[i] === arr[i + 1]) {
      duplicates.unshift(arr[i]);
    }
  }
  //filter out duplicates within "duplicates"
  duplicates = duplicates.filter((value, index) =>
     duplicates.indexOf(value) == index);
  return duplicates;
}

console.log(duplicates([1, 2, 4, 4, 3, 1, 5, '5'])); 

Trying to solve this Codwars Kata.

Given an array, find the duplicates in that array, and return a new array of those duplicates. The elements of the returned array should appear in the order when they first appeared as duplicates.

Examples:

[1, 2, 4, 4, 3, 3, 1, 5, 3, '5']  ==>  [4, 3, 1]
[0, 1, 2, 3, 4, 5]                ==>  []

I have:

function duplicates(arr) {

  arr.sort((value, index) => value - index);
  let duplicates = [];
  for (let i = 0; i < arr.length; i++) {
    if (arr[i] === arr[i + 1]) {
      duplicates.unshift(arr[i]);
    }
  }
  //filter out duplicates within "duplicates"
  duplicates = duplicates.filter((value, index) =>
     duplicates.indexOf(value) == index);
  return duplicates;
}

console.log(duplicates([1, 2, 4, 4, 3, 1, 5, '5'])); 

This is passing all tests except for one:

Expected: '[1, 4]', instead got: '[4, 1]'

And I'm not sure why - unfortunately it does not display the test case.

It was suggested that another way to create a frequency map, however, is with Map. How would I do this?

I tried:

function duplicates(arr) {

  let map = new Map([arr]);
  return map;

}

console.log(duplicates([1, 2, 4, 4, 3, 1, 5, '5'])); 

and this doesn't create a frequency map.

What other suggestions would you have?

NOTE - "5" and 5 should not count as the same value.

EDIT - Initially, tried to create a frequencyMap like this:

function duplicates(arr) {
  let map = {};
  arr.forEach((value, index) => {
    if (!map[value]) {
      map[value] = 0;
    }
    map[value] += 1;
  })
  return map;
}

console.log(duplicates([1, 2, 4, 4, 3, 1, 5, '5'])); 

But in this case, "5" and 5 are considered to be the same value. I don't know how else to check for duplicates - sorting disrupts the order in which the duplicates appear; and creating a frequencyMap count numbers and strings as the same thing.

Share Improve this question edited Jul 8, 2019 at 23:01 HappyHands31 asked Jun 25, 2019 at 23:31 HappyHands31HappyHands31 4,11119 gold badges66 silver badges117 bronze badges 4
  • 1 The instructions say: The elements of the returned array should appear in the order when they first appeared as duplicates. But the first thing you do is throw that information away by sorting the array. – Mark Commented Jun 25, 2019 at 23:34
  • I remember now why I sorted - I had tried to create a frequencyMap, but that counted 5 and "5" as the same thing, which is also against the rules. – HappyHands31 Commented Jun 25, 2019 at 23:44
  • Use a Map instead of an object to keep count. It distinguishes types for keys. – Mark Commented Jun 25, 2019 at 23:59
  • @MarkMeyer right, that's what I'm not understanding - how can I use Map to keep count? – HappyHands31 Commented Jun 26, 2019 at 0:11
Add a ment  | 

2 Answers 2

Reset to default 2

Here's an idea that should work:

Create a Map (map keys distinguish type so 5 is a different key than "5")

Use filter to go through the items in your array. As you go through keep count of how many times you've seen an item in your Map. Return true from the filter only when the count (before you've increased it) is 1. That's the second time you've seen that item.

The filter should return your answer:

function duplicates(arr) {
   let counts = new Map()
   return arr.filter(n => {
        let count = counts.get(n)
        counts.set(n, count ? count+1 : 1)
        return count === 1     
   })
}

console.log(duplicates([1, 2, 4, 4, 3, 1, 5, '5'])); 

Might not be the most efficient solution, but it solves the challenge. Note, I'm using js object to mimic a Map

 function duplicates(arr) {
  // TODO: return the array of duplicates from arr
  const map = {};
  const dup = {};

  for (const val of arr) {
    let key = val;
    if (typeof val === 'string') {
      key = `${val}_str`;
    }

    if (map[key]) {
      dup[val] = true;
    } else {
      map[key] = true;
    }
  }
  return Object.keys(dup)
  .map( d => (!Number.isInteger(parseInt(d))) ? d : Number(d));
}

console.log(duplicates([1, 2, 4, 4, 3, 1, 5, '5'])); 

Post a comment

comment list (0)

  1. No comments so far