根据工作日的小时数计算出小时数

时间:2011-04-10 12:00:07

标签: c# .net datetime

我正在尝试根据每天工作指定的小时数计算两个日期之间的天数。我无法确定在1天内选择了多少完整和半天,例如如果在日历上选择了1天,则实际上这将是1整天。

如果在第一天的09:00被选中并且在第2天说13:00那么这将是大约12个工作小时和1.5天。

编辑:最后也希望最后更新,这显示最终结果代码,以使问题在未来更具可读性

仍然需要添加银行假日检查等,但其大致存在)

//Validate working day rules are available
                    List<DayOfWeek> lDaysValidated = new List<DayOfWeek>();
                    double dTotalDays = 0;

                    //loop though the  days between the two dates
                    for ( var day = dtStartDate; day <= dtEndTime; day = day.AddDays( ( 1 ) ) )
                    {
                        //Only perform validation if the day of week has not already been validated
                        if ( !lDaysValidated.Contains( day.DayOfWeek ) )
                        {
                            //Look for working day rules for the user
                            List<UserTimeRule> lWorkingDayRules = UserTimeRule.GetUserTimeRules(
                                this.CurrentHolidayRequest.RequestedByID,
                                day.DayOfWeek,
                                false,
                                Settings.Instance.CostingModule,
                                TimeRuleRecordTypeEnum.DayRule );

                            //If the user has no rules, check the defaults
                            if ( lWorkingDayRules.Count == 0 )
                            {
                                //Get default rules for the day of week
                                lWorkingDayRules = UserTimeRule.GetDefaultUserTimeRules(
                                    day.DayOfWeek );

                                //If there is still no day rule, show error message and return
                                if ( lWorkingDayRules.Count == 0 )
                                {
                                    //Show error message
                                    lblWorkingDaysError.Text =
                                        String.Format(
                                            "* The current user has no working day rules set up, and there is no default day rule for '{0}'",
                                            day.DayOfWeek );

                                    return;
                                }
                                else
                                {
                                    //Calculate the working days
                                    this.CalculateWorkingDays(
                                       ref dtStartDate,
                                        ref dtEndTime,
                                        day,
                                        lWorkingDayRules,
                                        ref dTotalDays
                                        );

                                    //Add the day of week to the list of already validated days
                                    lDaysValidated.Add( day.DayOfWeek );
                                }
                            }
                            else
                            {
                                //Calculate the working days
                                this.CalculateWorkingDays(
                                   ref dtStartDate,
                                   ref dtEndTime,
                                    day,
                                    lWorkingDayRules,
                                    ref dTotalDays
                                    );

                                //Add the day of week to the list of already validated days
                                lDaysValidated.Add( day.DayOfWeek );
                            }
                        }
                    }

                    #endregion Validate

                    #region Update Details

                    //Set the Dates
                    this.CurrentHolidayRequestLine.StartTime = dtStartDate;
                    this.CurrentHolidayRequestLine.EndTime = dtEndTime;

                    //Set the number of Days
                    this.CurrentHolidayRequestLine.Days = Convert.ToDecimal( dTotalDays );

用来计算总天数的方法:

/// <summary>
        /// Calculates the number of working days for a specified day
        /// </summary>
        /// <param name="dtHolidayStartTime">The start time of the holiday request</param>
        /// <param name="dtHolidayEndTime">The end time of the holiday request</param>
        /// <param name="dtCurrentDay">The current day being evaluated</param>
        /// <param name="lWorkingDayRules">The current set of working day rules</param>
        /// <param name="dTotalDays">A reference to the total days on the request</param>
        [VersionChange( "7.3.88.271", "10/04/2011", "Method added to calculate No days on a request" )]
        private void CalculateWorkingDays( ref DateTime dtHolidayStartTime, ref DateTime dtHolidayEndTime, DateTime dtCurrentDay, List<UserTimeRule> lWorkingDayRules, ref double dTotalDays )
        {
            try
            {
                //Check whether Holiday start time is before the start time of the working day
                if ( dtHolidayStartTime.TimeOfDay < lWorkingDayRules[ 0 ].StartTime.TimeOfDay )
                {
                    dtHolidayStartTime = new DateTime(
                        dtHolidayStartTime.Year,
                        dtHolidayStartTime.Month,
                        dtHolidayStartTime.Day,
                        lWorkingDayRules[ 0 ].StartTime.Hour,
                        lWorkingDayRules[ 0 ].StartTime.Minute,
                        lWorkingDayRules[ 0 ].StartTime.Minute );
                }
                //Check whether the holiday end time is after the end time of a nomal working day
                if ( dtHolidayEndTime.TimeOfDay > lWorkingDayRules[ 0 ].EndTime.TimeOfDay )
                {
                    dtHolidayEndTime = new DateTime(
                        dtHolidayEndTime.Year,
                        dtHolidayEndTime.Month,
                        dtHolidayEndTime.Day,
                        lWorkingDayRules[ 0 ].EndTime.Hour,
                        lWorkingDayRules[ 0 ].EndTime.Minute,
                        lWorkingDayRules[ 0 ].EndTime.Minute );
                }
                //Check whether the holiday end time is after lunch time, but before the end of the day
                if ( dtHolidayEndTime.TimeOfDay > lWorkingDayRules[ 0 ].LunchEndTime.TimeOfDay
                    && dtHolidayEndTime.TimeOfDay < lWorkingDayRules[ 0 ].EndTime.TimeOfDay )
                {
                    dtHolidayEndTime = new DateTime(
                        dtHolidayEndTime.Year,
                        dtHolidayEndTime.Month,
                        dtHolidayEndTime.Day,
                        lWorkingDayRules[ 0 ].LunchEndTime.Hour,
                        lWorkingDayRules[ 0 ].LunchEndTime.Minute,
                        lWorkingDayRules[ 0 ].LunchEndTime.Minute );
                }

                //Create a date time object for the end current working day
                DateTime dtWorkingDayEndTime = new DateTime(
                    dtCurrentDay.Year,
                    dtCurrentDay.Month,
                    dtCurrentDay.Day,
                    lWorkingDayRules[ 0 ].EndTime.Hour,
                    lWorkingDayRules[ 0 ].EndTime.Minute,
                    lWorkingDayRules[ 0 ].EndTime.Second );

                //Create a date time object for the end of lunch
                DateTime dtWorkingDayLunchTime = new DateTime(
                    dtCurrentDay.Year,
                    dtCurrentDay.Month,
                    dtCurrentDay.Day,
                    lWorkingDayRules[ 0 ].LunchEndTime.Hour,
                    lWorkingDayRules[ 0 ].LunchEndTime.Minute,
                    lWorkingDayRules[ 0 ].LunchEndTime.Second );

                //Create a date time object for the start of the current day
                DateTime dtWorkingDayStartTime = new DateTime(
                    dtCurrentDay.Year,
                    dtCurrentDay.Month,
                    dtCurrentDay.Day,
                    lWorkingDayRules[ 0 ].StartTime.Hour,
                    lWorkingDayRules[ 0 ].StartTime.Minute,
                    lWorkingDayRules[ 0 ].StartTime.Second );

                //Check whether to add the first half of the day
                if ( dtHolidayEndTime >= dtWorkingDayLunchTime )
                {
                    dTotalDays += 0.5f;
                }

                //Check whether to add the second half of the day
                if ( dtHolidayEndTime >= dtWorkingDayEndTime )
                {
                    dTotalDays += 0.5f;
                }
            }
            catch ( Exception )
            {
                throw;
            }
        }

1 个答案:

答案 0 :(得分:1)

试试这个。这段代码不是用VS编写的,所以它可能并不完美......只使用其中的逻辑。

int htot = 0, dtot = 0;
while (date2>date1) {
  int h1 = date1.Hour < work_start ? work_start : date1.Hour;
  int h2 = date1.Hour > work_end ? work_end : date1.Hour;
  htot += (h2-h1);
  dtot++;
  date1 = date1.AddDays(1);
}