为了账号安全,请及时绑定邮箱和手机立即绑定

在 JavaScript 中计算不包括周末和联邦假期的前一个工作日

在 JavaScript 中计算不包括周末和联邦假期的前一个工作日

噜噜哒 2022-01-01 20:29:49
我正在编写一个函数,它将为我提供任何给定日期的前一个工作日。工作日意味着它是工作日,并且当天没有联邦假期。我的解决方案在今天(案例 1)是“2019-06-20T07:00:00.000Z”时有效;即星期四 // 返回星期三此外,当今天(情况 2)为“2019-06-24T07:00:00.000Z”时有效,即星期一 // 返回星期五但是当今天(情况 3)是 2019-05-28T07:00:00.000Z // 星期二时失败。对于情况 3,它应该返回前一个工作日为 5 月 24 日(星期五),因为星期一(5 月 27 日)是假期。对于案例 3,它返回 5 月 27 日,星期一。下面是我的代码,在我的 or 语句中我正在检查前一天,但它没有考虑到这一点,
查看完整描述

2 回答

?
青春有我

TA贡献1784条经验 获得超8个赞

您没有充分发挥 Luxon 的潜力。您应该将日期保留为 Luxon 对象,使用 Luxon 的方法对其进行所有操作,然后将日期转换为字符串。


为此,我定义了一个辅助函数prevBusinessDayHelper,该函数采用 Luxon 日期时间并返回表示前一个工作日的日期时间。它完全按照 Luxon 日期时间运行,这很容易。然后在外部函数中,我在 Luxon 日期时间之间进行转换。


const DateTime = luxon.DateTime;


// use a Set to make lookups cheaper

const federalHolidays = new Set([

  '2019-05-27', // <-- you were missing the 0 here in yours

  '2019-09-02',

  // snip

]);


// recursion is good here because it's very shallow

const prevBusinessDayHelper = dt => {


  // use luxon's tools!

  const yest = dt.minus({ days: 1 });


  if (yest.weekday == 6 || yest.weekday == 7 || federalHolidays.has(yest.toISODate()))

    return prevBusinessDayHelper(yest);


  return yest;

};


const prevBusinessDay = (isoString, zone) => {

  const dt = DateTime.fromISO(isoString).setZone(zone);

  return prevBusinessDayHelper(dt).toISODate();

};


console.log(prevBusinessDay("2019-05-28T07:00:00.000Z", "America/New_York"));

<script src="https://cdn.jsdelivr.net/npm/luxon@1.21.1/build/global/luxon.min.js"></script>


查看完整回答
反对 回复 2022-01-01
?
慕斯709654

TA贡献1840条经验 获得超5个赞

当您检查假期数组时,您正在检查完整日期而不是日期部分。


function check_previous_business_date(date, timezone) {

      const startDate = new Date(luxon.DateTime.fromISO(date).setZone(timezone));

      const todayTimeStamp = +new Date(startDate); // Unix timestamp in milliseconds

      const oneDayTimeStamp = 1000 * 60 * 60 * 24; // Milliseconds in a day

      const diff = todayTimeStamp - oneDayTimeStamp;

      const yesterdayDate = new Date(diff);

      const yesterdayString = yesterdayDate.getFullYear()

         + '-' + (yesterdayDate.getMonth() + 1) + '-' + yesterdayDate.getDate();

      for (startDate.setDate(startDate.getDate() - 1);

        !startDate.getDay() || startDate.getDay() === 6 ||

        federalHolidays.includes(startDate.toISOString().split('T')[0]) ||

        federalHolidays.includes(yesterdayString);

        startDate.setDate(startDate.getDate() - 1)

      ) { 

      }


      return startDate.toISOString().split('T')[0];

    }

const federalHolidays= [

  '2019-05-27',

  '2019-09-02',

  '2019-10-14',

  '2019-11-11'

];

console.log('Prev. day of 2019-05-28 is ',check_previous_business_date('2019-05-28T07:00:00.000Z', 'America/New_York'));

console.log('Prev. day of 2019-06-20 is ',check_previous_business_date('2019-06-20T07:00:00.000Z', 'America/New_York'));

<script src="https://cdn.jsdelivr.net/npm/luxon@1.21.1/build/global/luxon.min.js"></script>


查看完整回答
反对 回复 2022-01-01
  • 2 回答
  • 0 关注
  • 194 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
微信客服

购课补贴
联系客服咨询优惠详情

帮助反馈 APP下载

慕课网APP
您的移动学习伙伴

公众号

扫描二维码
关注慕课网微信公众号