How find if the current time exist in give time slots and find if the day is exist between given array of days

Viewed 61

Here is my days list

days_list: any[] = [
    {
      id: 0,
      value: 'Monday'
    },
    {
      id: 1,
      value: 'Tuesday'
    }, {
      id: 2,
      value: 'Wednesday'
    }, {
      id: 3,
      value: 'Thursday'
    }, {
      id: 4,
      value: 'Friday'
    }, {
      id: 5,
      value: 'Saturday'
    },
    {
      id: 6,
      value: 'Sunday'
    },
  ]

Here is my Business Hours

business_hours = { day_to: 2, time_to: "23:00", day_from: 5, time_from: "08:00" }

I'm using UTC date format I want to know if the day from days_list exist according to day_from and day_to

For example here day_from is 5 which is Saturday and day_to is 2 Wednesday so the required array is: ["Saturday", "Sunday", "Monday". "Tuesday". "Wednesday"] and the same for time if the current time exists in time_from and time_to,

My code is:

   const activationDate = new Date();

    const d_date = activationDate.getUTCDay() - 1;
    console.log(d_date);

    const B_from = this.getMin(this.business_hours.time_from);

    const B_To = this.getMin(this.business_hours.time_to);


    const min = activationDate.getUTCMinutes();
    console.log(min)
    const naan = activationDate.getUTCHours();
    console.log(naan)
    const utcTime = this.getUtcMin(naan, min);



    for(let j = 0; j < this.business_hours.day_to; j++) {
    for (let i = this.business_hours.day_from; i < this.days_list.length; i++) {
     
      console.log(this.days_list[i]);

      if (this.days_list[i].id === d_date) {
        this.is_open = true;
        console.log(this.days_list[i].value);
      }
     }
    }

it's not giving the required results.

3 Answers

My understanding is you'd like to treat your array as circular, and then slice it according to a "from" and "to" index, where both the "from" and "to" indexes are treated as inclusive.

Let's assume you have an array of strings like this:

console.log(dayArray);
// ["Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"] 

(which you can turn your structure into easily enough like:

const dayArray = days_list.reduce<string[]>((a, d) => (a[d.id] = d.value, a), []);

)

Then you can write a circular array slice with inclusive endpoints function in any number of ways. Here's one:

function circularArraySlice<T>(arr: T[], fromIndex: number, toIndex: number) {
  return arr.map((_, i, a) => a[(i + fromIndex) % a.length]).
    slice(0, ((arr.length + toIndex - fromIndex) % arr.length) + 1);
}

Essentially we're walking off the end of the array and back onto the beginning using modular arithmetic as (almost) implemented by the JS remainder operator (%). Let's see if it works:

console.log(circularArraySlice(dayArray, 5, 2));
// ["Saturday", "Sunday", "Monday", "Tuesday", "Wednesday"] 

console.log(circularArraySlice(dayArray, 2, 5));
// ["Wednesday", "Thursday", "Friday", "Saturday"]

This is, I think, what you want. There may well be edge cases so be careful.

Playground link to code

To help answer questions like this, I'd recommend listing a couple of test cases and both provide expected values and the values you're actually seeing.

But I can see a couple of things which may cause problems in the code:

  • The calculation of d_date is going to return -1 for Sunday, not 6 (like days_list is expecting)
  • The outer loop (the one setting j) isn't really adding a lot here, because j isn't used inside the loop. Therefore, each iteration of the loop is going to have the same effect.
  • The inner loop (the one setting i) is only looking for days which appear after day_from in your days_list array. However, as per you example, days from the start of days_list may also match if the day_from value is greater than day_to.

Based on Randy Casburn's (now-deleted) answer, it's possible to solve this using javascript's filter method. However, you need to be extra careful to handle separate cases for when to_date is before from_date and vice-versa.

For example:

const days_list = ['Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday', 'Sunday'];

function getDays(business_hours) {
  const days = days_list.filter((_, id) => {
      if (business_hours.day_from <= business_hours.day_to) {
        return (id >= business_hours.day_from && id <= business_hours.day_to);
      } else {
        return (id <= business_hours.day_to || id >= business_hours.day_from);
      }
  })
  console.log(business_hours, days);
  return days;
}
getDays({ day_from: 2, time_from: "23:00", day_to: 5, time_to: "08:00"});
getDays({ day_to: 2, time_to: "23:00", day_from: 5, time_from: "08:00"});
getDays({ day_from: 3, time_from: "23:00", day_to: 3, time_to: "08:00"});

Related