-2

I am trying to create an app, and got stuck at calculating if today is in the school year. The user enters two dates, with no year, that reoccur annually. These are the start and end dates of the school year.

I want to check if the current date, is between these two, even if it overlaps two years. So if school starts on November, and ends on june, if today is January 22nd, it should return true. But if its july, it should return false.

I did find this question: Php - work out what academic year it is, But it works on academic years, which don't have a holiday.

BTW I have joda time, if that helps.

Thanks in advance.

Community
  • 1
  • 1
michael_
  • 145
  • 9
  • 2
    Top answer to this post has a Joda Time solution: http://stackoverflow.com/questions/2896173/check-a-date-is-between-two-dates-in-java – CubeJockey May 01 '15 at 15:39
  • 1
    Or the brand new Java8 Date and Time features (based in Joda Time): http://www.oracle.com/technetwork/articles/java/jf14-date-time-2125367.html – Tavo May 01 '15 at 15:41
  • @BasilBourque This question isn't a duplicate. This is a more complicated case where you don't know the year of the start and end date. – michael_ May 02 '15 at 18:07
  • Duplicate Question: http://stackoverflow.com/q/27481579/642706 – Basil Bourque May 03 '15 at 22:05

3 Answers3

0
//parse both enddate/startdate to same year

if(enddate>startdate)
enddate+=1 year;

if(today>startdate and today<enddate)
return true;
saugata
  • 2,823
  • 1
  • 27
  • 39
0

Well, I thought for a bit and found a few solutions, but this seemed simplest.

private boolean isInSchoolYear(DateTime now, DateTime schoolYearStart, DateTime schoolYearEnd){
    int thisYear = now.getYear();
    schoolYearStart = schoolYearStart.withYear(thisYear);
    schoolYearEnd = schoolYearEnd.withYear(thisYear);

    if(schoolYearStart.isBefore(schoolYearEnd)){
        return new Interval(schoolYearStart, schoolYearEnd).contains(now);
    }
    else{
        return !(new Interval(schoolYearEnd, schoolYearStart).contains(now));
    }
}

This way it works both if the school year overlaps 2 years or 1.

michael_
  • 145
  • 9
0

Question Is Unclear

Your question is unclear.

For one thing, if the user is entering dates without a year, then they are not entering dates. They are entering a month number and a day-of-month number.

Perhaps the question is:

Determine if a given target date (perhaps today) is contained within either of two intervals defined by a pair of month & day-of-month numbers (a "MonthDay") where we consider the pair to either (a) end in the date’s year or (b) begin in the date’s year. We assume the pair represents a span of time of less than one year.

Joda-Time

If that is the Question, then here is some code using Joda-Time 2.7. Two caveats:

  • You could probably do something shorter using clever comparisons of month numbers and day-of-month numbers. But to be educational, and allow more flexibility for similar problems, I'm using Joda-Time features.
  • Only minimal thought and testing has gone into this code. Try various values for more testing, and re-consider the logic before using in production.

Turns out that Joda-Time has a MonthDay class, just what you need.

MonthDay mdStart = new MonthDay ( DateTimeConstants.NOVEMBER, 1 );
MonthDay mdStop = new MonthDay ( DateTimeConstants.JUNE, 1 );

Note that time zone is critical in determining the month & day of a moment such as now. For example, at a moment after midnight in Paris, it is still ‘yesterday’ in Montréal. Use proper time zone names, never the 3-4 letter codes.

DateTime target = DateTime.now ( DateTimeZone.forID ( "Africa/Casablanca" ) ); // Using current date-time, but could be any date-time.

The toDateTime method takes data fields from the MonthDay (the month number and the day number) and applies them to an existing DateTime to create a new DateTime instance. Joda-Time uses immutable objects, so we create a new instance based on the old instance rather than modify the old.

Let’s consider two possible span of times:

  • Where the pair of MonthDay objects are a span of time ending in the year of the target DateTime. (an earlier interval)
  • Where the pair of MonthDay objects are a span of time beginning in the year of the target DateTime. (a later interval)

First, the earlier interval.

// Determine a span of time, moving the Start to previous year if need be.
DateTime earlierStart = mdStart.toDateTime ( target ); // Overlay the data fields of the MonthDay on top of the data fields of a DateTime to create a new DateTime object.
DateTime earlierStop = mdStop.toDateTime ( target );
if ( earlierStart.isAfter ( earlierStop ) ) {  // If the start would land after the stop, then adjust the start to *previous* year.
    earlierStart = earlierStart.minusYears ( 1 );
}

Joda-Time also offers the Interval class for defining a span of time as a pair of specific points along the timeline.

Interval earlierInterval = new Interval ( earlierStart, earlierStop );

// Determine a span of time, moving the Stop to next year if need be.
DateTime laterStart = mdStart.toDateTime ( target ); // Overlay the data fields of the MonthDay on top of the data fields of a DateTime to create a new DateTime object.
DateTime laterStop = mdStop.toDateTime ( target );
if ( laterStart.isAfter ( laterStop ) ) {  // If the start would land after the stop, then adjust the start to *next* year.
    laterStop = laterStop.plusYears ( 1 );
}
Interval laterInterval = new Interval ( laterStart, laterStop );

Now test if the target DateTime is contained within the Interval. Note that Joda-Time wisely uses the Half-Open approach to defining a span of time, where the beginning is inclusive while the ending is exclusive. So, in our example June 1st is not within our range. That means if the target were November 1st we would have a hit, but if the target were June 1st we would have a miss.

Boolean earlierHasTarget = earlierInterval.contains ( target );
Boolean laterHasTarget = laterInterval.contains ( target );

Boolean targetContained = ( earlierHasTarget || laterHasTarget );

java.time

Java 8 has java.time, a new date-time framework inspired by Joda-Time. While largely similar to Joda-Time, it is not a direct replacement. Each has features the other lacks. In particular, java.time lacks any equivalent to Interval.

Basil Bourque
  • 303,325
  • 100
  • 852
  • 1,154