如何修复Java程序无法打印指定年份所有周五的问题?
问题:Java程序无法输出2022年的所有周五
我编写了一个Java程序,想要打印任意年份的周五和周六,但运行时发现针对2022年,程序只输出了周六,完全没有显示周五,其他年份未出现该异常。以下是我的代码及对应输出:
import java.util.Calendar; import java.util.GregorianCalendar; import java.util.Scanner; public class JavaDayFinder extends Thread { int day; int year; JavaDayFinder(int day, int year) { this.day = day; this.year = year; } @Override public void run() { Calendar calendar = new GregorianCalendar(); calendar.set(year, Calendar.JANUARY, 1); calendar.getTime(); calendar.set(Calendar.DAY_OF_WEEK, day); calendar.getTime(); while (calendar.get(Calendar.YEAR) == year) { System.out.println(calendar.getTime()); calendar.add(Calendar.DAY_OF_MONTH, 7); try { Thread.sleep(250); } catch (InterruptedException e) { throw new RuntimeException(e); } } } public static void main(String[] args) { System.out.println("This program prints all the common holidays (Fridays & Saturdays) of any given year."); System.out.print("Please input the year of which you want to know the holidays: "); Scanner scan = new Scanner(System.in); int year = scan.nextInt(); System.out.println("Given year : " + year); System.out.println(); JavaDayFinder friday = new JavaDayFinder(6, year); JavaDayFinder saturday = new JavaDayFinder(7, year); friday.start(); saturday.start(); } }
程序输出(2022年)
This program prints all the common holidays (Fridays & Saturdays) of any given year. Please input the year of which you want to know the holidays: 2022 Given year : 2022 Sat Jan 01 17:05:56 BDT 2022 Sat Jan 08 17:05:56 BDT 2022 Sat Jan 15 17:05:56 BDT 2022 Sat Jan 22 17:05:56 BDT 2022 Sat Jan 29 17:05:56 BDT 2022 Sat Feb 05 17:05:56 BDT 2022 Sat Feb 12 17:05:56 BDT 2022 Sat Feb 19 17:05:56 BDT 2022 Sat Feb 26 17:05:56 BDT 2022 Sat Mar 05 17:05:56 BDT 2022 Sat Mar 12 17:05:56 BDT 2022 Sat Mar 19 17:05:56 BDT 2022 Sat Mar 26 17:05:56 BDT 2022 Sat Apr 02 17:05:56 BDT 2022 Sat Apr 09 17:05:56 BDT 2022 Sat Apr 16 17:05:56 BDT 2022 Sat Apr 23 17:05:56 BDT 2022 Sat Apr 30 17:05:56 BDT 2022 Sat May 07 17:05:56 BDT 2022 Sat May 14 17:05:56 BDT 2022 Sat May 21 17:05:56 BDT 2022 Sat May 28 17:05:56 BDT 2022 Sat Jun 04 17:05:56 BDT 2022 Sat Jun 11 17:05:56 BDT 2022 Sat Jun 18 17:05:56 BDT 2022 Sat Jun 25 17:05:56 BDT 2022 Sat Jul 02 17:05:56 BDT 2022 Sat Jul 09 17:05:56 BDT 2022 Sat Jul 16 17:05:56 BDT 2022 Sat Jul 23 17:05:56 BDT 2022 Sat Jul 30 17:05:56 BDT 2022 Sat Aug 06 17:05:56 BDT 2022 Sat Aug 13 17:05:56 BDT 2022 Sat Aug 20 17:05:56 BDT 2022 Sat Aug 27 17:05:56 BDT 2022 Sat Sep 03 17:05:56 BDT 2022 Sat Sep 10 17:05:56 BDT 2022 Sat Sep 17 17:05:56 BDT 2022 Sat Sep 24 17:05:56 BDT 2022 Sat Oct 01 17:05:56 BDT 2022 Sat Oct 08 17:05:56 BDT 2022 Sat Oct 15 17:05:56 BDT 2022 Sat Oct 22 17:05:56 BDT 2022 Sat Oct 29 17:05:56 BDT 2022 Sat Nov 05 17:05:56 BDT 2022 Sat Nov 12 17:05:56 BDT 2022 Sat Nov 19 17:05:56 BDT 2022 Sat Nov 26 17:05:56 BDT 2022 Sat Dec 03 17:05:56 BDT 2022 Sat Dec 10 17:05:56 BDT 2022 Sat Dec 17 17:05:56 BDT 2022 Sat Dec 24 17:05:56 BDT 2022 Sat Dec 31 17:05:56 BDT 2022 Process finished with exit code 0
问题原因与修复方案
错误根源
问题出在Calendar.set(Calendar.DAY_OF_WEEK, day)的行为逻辑上:
- 2022年1月1日是周六(对应
Calendar.SATURDAY=7) - 当你把日历设置到2022年1月1日后,调用
set(Calendar.DAY_OF_WEEK, 6)(周五)时,Calendar会自动向前调整到最近的上一个周五,也就是2021年12月31日 - 此时日历的年份是2021,不满足
while (calendar.get(Calendar.YEAR) == year)的循环条件,所以周五的循环直接跳过,没有任何输出
修复方法
不要直接设置DAY_OF_WEEK,而是从1月1日开始计算需要添加多少天才能到达目标星期几,确保不会跳到上一年:
修改run()方法中的日历初始化逻辑:
@Override public void run() { Calendar calendar = new GregorianCalendar(); calendar.set(year, Calendar.JANUARY, 1); // 计算从1月1日到目标星期几需要添加的天数 int currentDayOfWeek = calendar.get(Calendar.DAY_OF_WEEK); int daysToAdd = (day - currentDayOfWeek + 7) % 7; // 如果计算结果为0,说明1月1日就是目标星期几,不需要额外添加 if (daysToAdd != 0) { calendar.add(Calendar.DAY_OF_MONTH, daysToAdd); } while (calendar.get(Calendar.YEAR) == year) { System.out.println(calendar.getTime()); calendar.add(Calendar.DAY_OF_MONTH, 7); try { Thread.sleep(250); } catch (InterruptedException e) { throw new RuntimeException(e); } } }
另外,建议直接使用Calendar.FRIDAY和Calendar.SATURDAY常量代替硬编码的6和7,提高代码可读性:
JavaDayFinder friday = new JavaDayFinder(Calendar.FRIDAY, year); JavaDayFinder saturday = new JavaDayFinder(Calendar.SATURDAY, year);
额外建议
Calendar类已经过时,推荐使用Java 8引入的java.time包(如LocalDate、DayOfWeek),API更清晰不易出错,示例代码如下:
import java.time.DayOfWeek; import java.time.LocalDate; import java.util.Scanner; public class DayFinder { public static void printDays(int year, DayOfWeek targetDay) { LocalDate date = LocalDate.of(year, 1, 1); // 调整到第一个目标星期几 date = date.with(targetDay); // 如果调整后到了下一年,就加7天回到当前年 if (date.getYear() != year) { date = date.plusWeeks(1); } while (date.getYear() == year) { System.out.println(date); date = date.plusWeeks(1); } } public static void main(String[] args) { System.out.println("该程序将打印指定年份的所有周五和周六"); System.out.print("请输入年份:"); Scanner scan = new Scanner(System.in); int year = scan.nextInt(); System.out.println("指定年份:" + year); System.out.println(); printDays(year, DayOfWeek.FRIDAY); printDays(year, DayOfWeek.SATURDAY); } }
内容的提问来源于stack exchange,提问作者Monirul Islam
相关产品推荐
相关产品推荐

