Ashik Paul
Ashik Paul

Reputation: 504

How to get repeating week dates count between a date range in JavaScript?

I have an array of date-ranges from which I need to know how many people have worked in each week for the whole year.

Eg: mainArray = ['01-01-2020','31-12-2020']; //year range

dateRanges = [
  [01-01-2020, 03-01-2020], //week 1
  [03-01-2020, 06-01-2020], //week 1 and 2
  [09-01-2020, 09-01-2020], //week 2
  [10-01-2020, 11-01-2020], //week 2
  [22-01-2020, 23-01-2020], //week 4
  ....
];

//first we need to find all the weeks from the mainArray date-range 

//then calculate the weeks colliding in the dateRanges array.

the output should be =>

workLoadInWeeks = [2,3,0,1,0,0,0,0,......,0];

Explanation: Since 03-01-2020(date in week-1) is repeating in 1st and 2nd array indexes, that's why the output has 2 as the first value.

Since the dates of week-2 are repeating in dateRanges[1], dateRanges[2], dateRanges[3], that's why the output has 3 as the second value.

since nobody worked in 3rd week its 0 in the output array

Week start - Sunday, 7 days a week,
I want the week date range to start from the 1st Jan, so first week would be a partial week as 1st start is a Wednesday.

This may sound confusing. I have tried my best to explain.

Upvotes: 2

Views: 286

Answers (2)

StepUp
StepUp

Reputation: 38094

We need a function which results overall count of week:

function getISOWeeks(y) {
    var d,
        isLeap;

    d = new Date(y, 0, 1);
    isLeap = new Date(y, 1, 29).getMonth() === 1;

    //check for a Jan 1 that's a Thursday or a leap year that has a
    //Wednesday jan 1. Otherwise it's 52
    return d.getDay() === 4 || isLeap && d.getDay() === 3 ? 53 : 52
}

And a function which gets week number:

function getWeek(date_string) {
    let [d, M, y] = date_string.split(/[- :]/);
    let passedDate = new Date(y, parseInt(M) - 1, d);
    let onejan = new Date(passedDate.getFullYear(), 0, 1);
    week = Math.ceil( (((passedDate - onejan) / 86400000) + onejan.getDay() + 1) / 7 );
    return week;
} 

After we having this weeks we counts of persons per Week. And then we can figure out how many people have worked in each week for the whole year.

let weeks = dateRanges.map(s => s.map(d => this.getWeek(d)));

let distinctWeeks = weeks.map(s => 
    s.filter((item, pos) => s.indexOf(item) == pos)).flatMap(s => s);

let personPerWeek = distinctWeeks.reduce((a, c)=> {
    a[c] = a[c] || 0;
    a[c] += 1;
    return a;
},{})

const weekCount = getISOWeeks(2020);
let personsPerWeeks = [];

getWorkWeeks = (workWeeks, weekCount) => {
    for (let index = 1; index <= weekCount; index++) {
        let personCount = personPerWeek[index] || 0;
        workWeeks.push(personCount);
    }
    return workWeeks;
}

An example can be seen here:

function getWeek(date_string) {
    let [d, M, y] = date_string.split(/[- :]/);
    let passedDate = new Date(y, parseInt(M) - 1, d);
    let onejan = new Date(passedDate.getFullYear(), 0, 1);
    week = Math.ceil( (((passedDate - onejan) / 86400000) + onejan.getDay() + 1) / 7 );
    return week;
}

function getISOWeeks(y) {
    var d,
        isLeap;

    d = new Date(y, 0, 1);
    isLeap = new Date(y, 1, 29).getMonth() === 1;
    //check for a Jan 1 that's a Thursday or a leap year that has a
    //Wednesday jan 1. Otherwise it's 52
    return d.getDay() === 4 || isLeap && d.getDay() === 3 ? 53 : 52
}

let dateRanges = [
  ['01-01-2020', '03-01-2020'], //week 1
  ['03-01-2020', '06-01-2020'], //week 1 and 2
  ['09-01-2020', '09-01-2020'], //week 2
  ['10-01-2020', '11-01-2020'], //week 2
  ['22-01-2020', '23-01-2020'], //week 4
];

let weeks = dateRanges.map(s => s.map(d => this.getWeek(d)));
let distinctWeeks = weeks.map(s => s.filter((item, pos) => s.indexOf(item) == pos)).flatMap(s => s);
let personPerWeek = distinctWeeks.reduce((a, c)=> {
    a[c] = a[c] || 0;
    a[c] += 1;
    return a;
},{})

const weekCount = getISOWeeks(2020);
let personsPerWeeks = [];

getWorkWeeks = (workWeeks, weekCount) => {
    for (let index = 1; index <= weekCount; index++) {
        let personCount = personPerWeek[index] || 0;
        workWeeks.push(personCount);
    }
    return workWeeks;
}

getWorkWeeks(personsPerWeeks, weekCount);
console.log(personsPerWeeks)

Upvotes: 1

Avinash Dalvi
Avinash Dalvi

Reputation: 9301

Check if this works for you.

dateRanges = [
 ["01-01-2020", "03-01-2020"], //week 1
  ["03-01-2020", "06-01-2020"], //week 1 and 2
  ["09-01-2020", "09-01-2020"], //week 2
  ["10-01-2020", "11-01-2020"], //week 2
  ["22-01-2020", "23-01-2020"], //week 4

];

mainArray = ['01-01-2020','31-12-2020'];
//console.log(dateRanges);
function diff_weeks(dt2, dt1) 
 {

  var diff =(dt2.getTime() - dt1.getTime()) / 1000;
  diff /= (60 * 60 * 24 * 7);
  return Math.abs(Math.round(diff));
  
 }

//for(var i = 0; i< dateRanges.length;i++){
//console.log(dateRanges[i][0]);
  var dateString1 = mainArray[0];
  var dateParts1 = dateString1.split("-"); 
  var dt1 = new Date(+dateParts1[2], dateParts1[1] - 1, +dateParts1[0]); 
  var dateString2 = mainArray[1];
  var dateParts2 = dateString2.split("-"); 
  var dt2 = new Date(+dateParts2[2], dateParts2[1] - 1, +dateParts2[0]); 
  //console.log(dt1);
  console.log(diff_weeks(dt1, dt2) + " Weeks");
//}

Upvotes: 0

Related Questions