Home > Software design >  find duplicated values in array and return how many time or 0?
find duplicated values in array and return how many time or 0?

Time:12-13

i have an array of dates:

let arr = ['02-11-2022', '02-11-2022', '03-11-2022', '04-11-2022', '04-11-2022', '04-11-2022', '05-11-2022', '07-11-2022'];

i want to search which dates are duplicated and how much times? and if date is skiped like 06-11-2022 so it will be 0 (like saving space). return all that in new array like that:

let new = [2,1,3,1,0,1];

i want to save space so i could compare later:

arr[0] == new[0]...
arr[3] == new[3]...
arr[5] == new[5]...

i tried many function but couldnt save space or count it in the correct way.

thank you.

CodePudding user response:

const dateCount = {};
const dates = ['02-11-2022', '02-11-2022', '03-11-2022', '04-11-2022', '04-11-2022', '04-11-2022', '05-11-2022', '07-11-2022'];
dates.forEach((date) => {
    dateCount[date] = (dateCount[date] || 0)   1;
})

console.log(dateCount)

CodePudding user response:

An algorithm for this could be:

let arr = ['02-11-2022', '02-11-2022', '03-11-2022', '04-11-2022', '04-11-2022', '04-11-2022', '05-11-2022', '07-11-2022'];

const duplicates = [];

let currentDuplicates = 0;
let previousDate = arr[0].slice(0, 2);
while(arr.length) {
    const element = arr[0];
    
    arr = arr.filter((comparedElement) => {
        const isEqual = comparedElement === element;
        if (isEqual) {
            currentDuplicates  = 1;
        }

        return !isEqual;
    });

    // the quantity of days between today and the last day is greater than 1
    const currentDay = element.slice(0, 2);
    const skippedDays = currentDay - previousDate;
    const hasSkippedDays = skippedDays > 1;

    if (hasSkippedDays) {
        duplicates.push(...'0'.repeat(skippedDays - 1).split('').map((n) => Number(n)));
    }

    duplicates.push(currentDuplicates);
    currentDuplicates = 0;
    previousDate = currentDay;
}

While the array has an element, we filter and, at the same time, count how many times we finded an element equal to our current element. And before we push the duplicate into the array, we check how many days passed between today and the last parsed day.

This is how my brain instinctively thinks, so I would try to refactor for more performance gains!

An observation too, is that the code only compares the number of days between two dates, so if you skip a month or a yearlike let arr = ['01-01-2000', '01-12-2000', '01-12-9999'] , it'll not recognize the skipped days :)


A quick built-in solution to find the total of duplicates could be getting the array length with the duplicates:

const arraySize = arr.length;

Transform the array in a set. Sets by nature doesn't allow duplicates, then you just need to find the difference between the two lengths:

const set = new Set(arr);
const totalDuplicates = arraySize - set.size;

CodePudding user response:

You could have something like this to count duplicates in your array:

const dateCounter = (dates) => {

  const dateObjects = dates.map(dateString => {
    const parts = dateString.split('-');
    const [day, month, year] = [parts[0], parts[1], parts[2]];
    return new Date(`${month}/${day}/${year}`);
  });

  const counts = {}
  const duplicates = []
  const missingDates = [];
 
  for (let i = 1; i < dateObjects.length; i  ) {
    const diff = dateObjects[i].getTime() - dateObjects[i - 1].getTime();

    if (diff > 86400000) {
      const numMissingDates = Math.floor(diff / 86400000) - 1;
      for (let j = 1; j <= numMissingDates; j  ) {
        const missingDate = new Date(dateObjects[i - 1].getTime()   (j * 86400000))
        missingDates.push(missingDate);
        counts[missingDate] = 0
      }
    } 
     
    counts[dateObjects[i]] = i !== 1 ? (counts[dateObjects[i]] || 0)   1 : (counts[dateObjects[i]] || 1)   1;

  }

  for (const key in counts) {
     duplicates.push(counts[key]);
  }

  return duplicates

}

This is how you would execute it as an example:

const arr = ['02-11-2022', '02-11-2022', '03-11-2022', '04-11-2022', '04-11-2022', '04-11-2022', '05-11-2022', '07-11-2022'];
const duplicates = dateCounter(arr);
console.log(duplicates); // [2, 1, 3, 1, 0, 1]
  • Related