using Jiaowu.Api.Domain.Academic; namespace Jiaowu.Api.Infrastructure.Teaching; public static class TeachingTaskHours { public static int Calculate(int startWeek, int endWeek, int weeklyHours) => endWeek < startWeek ? 0 : (endWeek - startWeek + 1) * weeklyHours; public static int RegularScheduleHours(Course course) => RegularScheduleHours(course.TotalHours, course.PracticeHours); public static int RegularScheduleHours(int totalHours, int practiceHours) => Math.Max(0, totalHours - practiceHours); public static int TargetHours( Course course, TeachingTaskSchedulingMode schedulingMode) => course.TotalHours; public static int TargetHours(Course course, ScheduleEntryKind kind) => kind == ScheduleEntryKind.Experiment ? Math.Max(0, course.PracticeHours) : RegularScheduleHours(course); public static int ScheduledHours(ScheduleEntry entry) => ScheduledHours( entry.StartWeek, entry.EndWeek, entry.WeekPattern, entry.PeriodCount); public static int ScheduledHours( int startWeek, int endWeek, WeekPattern weekPattern, int periodCount) { if (endWeek < startWeek || periodCount <= 0) return 0; var occurrences = Enumerable.Range(startWeek, endWeek - startWeek + 1) .Count(week => weekPattern == WeekPattern.All || weekPattern == WeekPattern.Odd && week % 2 == 1 || weekPattern == WeekPattern.Even && week % 2 == 0); return occurrences * periodCount; } public static bool TryResolveRegularWeeklyHours( Course course, int startWeek, int endWeek, out int weeklyHours) => TryResolveRegularWeeklyHours( course.TotalHours, course.PracticeHours, startWeek, endWeek, out weeklyHours); public static bool TryResolveRegularWeeklyHours( int totalHours, int practiceHours, int startWeek, int endWeek, out int weeklyHours) { weeklyHours = 0; var weekCount = endWeek - startWeek + 1; var regularHours = RegularScheduleHours(totalHours, practiceHours); if (weekCount <= 0 || regularHours % weekCount != 0) return false; weeklyHours = regularHours / weekCount; return true; } public static string? Validate( Course course, int startWeek, int endWeek, int weeklyHours, TeachingTaskSchedulingMode schedulingMode = TeachingTaskSchedulingMode.Standard) { var plannedHours = Calculate(startWeek, endWeek, weeklyHours); var targetHours = TargetHours(course, schedulingMode); if (plannedHours == targetHours) return null; if (schedulingMode == TeachingTaskSchedulingMode.Standard) { return $"课程“{course.Name}”总学时为 {course.TotalHours},其中实践学时 " + $"{course.PracticeHours};理论课和实验课均应进入课表。当前第 " + $"{startWeek}—{endWeek} 周、每周 {weeklyHours} 学时,共 " + $"{plannedHours} 学时。请调整授课周次或周学时。"; } return $"课程“{course.Name}”总学时为 {course.TotalHours};当前第 " + $"{startWeek}—{endWeek} 周、每周 {weeklyHours} 学时,共 " + $"{plannedHours} 学时。请调整授课周次或周学时。"; } }