You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何修复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

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.18 05:01:06