Issue
"I have been assigned the task of programming a calculator in Java (C# would also work) that, based on the current year and user input, outputs the dates for the earliest and latest Easter Sunday. The program should work in such a way that the user enters a number representing the number of years to be checked in the future. The current year is 2023. The output should then display the earliest and latest dates on which Easter Sunday occurred within the specified number of years.
Unfortunately, my code doesn't seem to solve it. The calculation of Easter Sundays is correct, but for some reason, filtering for the earliest and latest Easter Sunday doesn't seem to work."
import java.time.LocalDate;
import java.util.Scanner;
public class Ostersonntag3 {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
System.out.print("Bitte geben Sie eine Anzahl an Jahren ein: ");
int x = scanner.nextInt();
LocalDate spätesterOstersonntag = LocalDate.MAX;
LocalDate frühesterOstersonntag = LocalDate.MIN;
int currentYear = 2023;
for (int i = 0; i < x; i++) {
LocalDate ostersonntag = berechneOstersonntag(currentYear +
i);
if (ostersonntag.isBefore(spätesterOstersonntag)) {
spätesterOstersonntag = ostersonntag;
}
if (ostersonntag.isAfter(frühesterOstersonntag)) {
frühesterOstersonntag = ostersonntag;
}
}
System.out.println("Spaetester Ostersonntag: " +
spätesterOstersonntag);
System.out.println("Fruehester Ostersonntag: " +
frühesterOstersonntag);
scanner.close();
}
private static LocalDate berechneOstersonntag(int jahr) {
int a = jahr % 19;
int b = jahr % 4;
int c = jahr % 7;
int m = (8 * (jahr / 100) + 13) / 25 - 2;
int s = jahr / 100 - jahr / 400 - 2;
int n = (6 + s) % 7;
int d = (m + 19 * a) % 30;
if (d == 29) {
d = 28;
}
if (d == 28 && a >= 11) {
d = 27;
}
int e = (2 * b + 4 * c + 6 * d + n) % 7;
int tag = 21 + d + e + 1;
int monat;
if (tag > 31) {
tag = tag % 31;
monat = 4;
} else {
monat = 3;
}
return LocalDate.of(jahr, monat, tag);
}
}
The Input is as you can see a number (int) and the Output that i want is a date (for example 2023.04.22, etc.) the dates should represent the earliest and latest easter sunday in the amount of years the user put in. But the Output does not seem to be giving me the correct dates: [(for example the input is 20; the output is 2023.04.16 as the latest easter sunday and 2023.04.20 is the date for the closest easter sunday) (But if the Input is 200; the output is 2023.04.16 for the latest and 2023.04.14 for the earliest easter sunday) (And if the input is 30; the output is 2023.04.16 for the latest and 2023.03.31 for the earliest easter sunday)]. This does not make sense for me like at all??
Solution
One problem is that you are incrementing years. And using the isBefore
and isAfter
methods also include the year which is incorrectly reporting min
and max
dates for Easter. Example. 2023-04-09 isBefore 2024-03-31
from a date perspective but not from a month/day
perspective. Note: I had to print the actual values you were comparing to see what was going on and at first it wasn't obvious to me. Print statements are your friend when it comes to debugging. So you just compare the day of the year to previous days of the year for Easter. So here is what I did.
- define a comparator to compare month and day using the day of year.
- initialize your
min
andmax
to the current year date for Easter. - then starting with '1', increment your years.
int x = 20;
int currentYear = 2023;
Comparator<LocalDate> comp = Comparator.comparing(LocalDate::getDayOfYear);
LocalDate ostersonntag = berechneOstersonntag(currentYear);
LocalDate spätesterOstersonntag = ostersonntag;
LocalDate frühesterOstersonntag = ostersonntag;
for (int i = 0; i < x; i++) {
ostersonntag = berechneOstersonntag(currentYear +
i);
if (comp.compare(ostersonntag, spätesterOstersonntag) > 0) {
spätesterOstersonntag = ostersonntag;
} else if (comp.compare(ostersonntag, frühesterOstersonntag) < 0) {
frühesterOstersonntag = ostersonntag;
}
}
System.out.println("Spaetester Ostersonntag: " +
spätesterOstersonntag);
System.out.println("Fruehester Ostersonntag: " +
frühesterOstersonntag);
}
prints
Spaetester Ostersonntag: 2038-04-25
Fruehester Ostersonntag: 2035-03-25
Note: Another issue is that you and I are using different calculations to determine Easter. I used this algorithm posted by @VGR. I verified the above using Easter Dates
Answered By - WJS
0 comments:
Post a Comment
Note: Only a member of this blog may post a comment.