3
\$\begingroup\$

I've created a method to split a date range into a collection of date-arrays. These arrays consist of two timestamps.

Example:

        System.out.println("");
        System.out.println("*****************************");
        System.out.println("Split 2.1.2004 to 26.3.2004: ");
        for (DateTime[] date : TimeSplitter.splitDateIntoMonths(new DateTime(2004, 1, 2, 0, 0, 0, 0).toDate(),
                new DateTime(2004, 3, 26, 0, 0, 0, 0).toDate())) {

            System.out.println(date[0] + " and " + date[1]);

        }

        System.out.println("");
        System.out.println("*****************************");
        System.out.println("Split 1.1.2000 to 31.12.2005: ");
        for (DateTime[] date : TimeSplitter.splitDateIntoMonths(new DateTime(2000, 1, 1, 0, 0, 0, 0).toDate(),
                new DateTime(2005, 12, 31, 0, 0, 0, 0).toDate())) {

            System.out.println(date[0] + " and " + date[1]);

        }

Results into:

*****************************
Split 2.1.2004 to 26.3.2004: 
2004-01-02T00:00:00.000+01:00 and 2004-01-31T00:00:00.000+01:00
2004-02-01T00:00:00.000+01:00 and 2004-02-29T00:00:00.000+01:00
2004-03-01T00:00:00.000+01:00 and 2004-03-26T00:00:00.000+01:00

*****************************
Split 1.1.2000 to 31.12.2005: 
2000-01-01T00:00:00.000+01:00 and 2000-01-31T00:00:00.000+01:00
2000-02-01T00:00:00.000+01:00 and 2000-02-29T00:00:00.000+01:00
2000-03-01T00:00:00.000+01:00 and 2000-03-31T00:00:00.000+02:00
2000-04-01T00:00:00.000+02:00 and 2000-04-30T00:00:00.000+02:00
2000-05-01T00:00:00.000+02:00 and 2000-05-31T00:00:00.000+02:00
2000-06-01T00:00:00.000+02:00 and 2000-06-30T00:00:00.000+02:00
2000-07-01T00:00:00.000+02:00 and 2000-07-31T00:00:00.000+02:00
2000-08-01T00:00:00.000+02:00 and 2000-08-31T00:00:00.000+02:00
2000-09-01T00:00:00.000+02:00 and 2000-09-30T00:00:00.000+02:00
2000-10-01T00:00:00.000+02:00 and 2000-10-31T00:00:00.000+01:00
2000-11-01T00:00:00.000+01:00 and 2000-11-30T00:00:00.000+01:00
2000-12-01T00:00:00.000+01:00 and 2000-12-31T00:00:00.000+01:00
2001-01-01T00:00:00.000+01:00 and 2001-01-31T00:00:00.000+01:00
2001-02-01T00:00:00.000+01:00 and 2001-02-28T00:00:00.000+01:00
2001-03-01T00:00:00.000+01:00 and 2001-03-31T00:00:00.000+02:00
2001-04-01T00:00:00.000+02:00 and 2001-04-30T00:00:00.000+02:00
2001-05-01T00:00:00.000+02:00 and 2001-05-31T00:00:00.000+02:00
2001-06-01T00:00:00.000+02:00 and 2001-06-30T00:00:00.000+02:00
2001-07-01T00:00:00.000+02:00 and 2001-07-31T00:00:00.000+02:00
2001-08-01T00:00:00.000+02:00 and 2001-08-31T00:00:00.000+02:00
2001-09-01T00:00:00.000+02:00 and 2001-09-30T00:00:00.000+02:00
2001-10-01T00:00:00.000+02:00 and 2001-10-31T00:00:00.000+01:00
2001-11-01T00:00:00.000+01:00 and 2001-11-30T00:00:00.000+01:00
2001-12-01T00:00:00.000+01:00 and 2001-12-31T00:00:00.000+01:00
2002-01-01T00:00:00.000+01:00 and 2002-01-31T00:00:00.000+01:00
2002-02-01T00:00:00.000+01:00 and 2002-02-28T00:00:00.000+01:00
2002-03-01T00:00:00.000+01:00 and 2002-03-31T00:00:00.000+01:00
2002-04-01T00:00:00.000+02:00 and 2002-04-30T00:00:00.000+02:00
2002-05-01T00:00:00.000+02:00 and 2002-05-31T00:00:00.000+02:00
2002-06-01T00:00:00.000+02:00 and 2002-06-30T00:00:00.000+02:00
2002-07-01T00:00:00.000+02:00 and 2002-07-31T00:00:00.000+02:00
2002-08-01T00:00:00.000+02:00 and 2002-08-31T00:00:00.000+02:00
2002-09-01T00:00:00.000+02:00 and 2002-09-30T00:00:00.000+02:00
2002-10-01T00:00:00.000+02:00 and 2002-10-31T00:00:00.000+01:00
2002-11-01T00:00:00.000+01:00 and 2002-11-30T00:00:00.000+01:00
2002-12-01T00:00:00.000+01:00 and 2002-12-31T00:00:00.000+01:00
2003-01-01T00:00:00.000+01:00 and 2003-01-31T00:00:00.000+01:00
2003-02-01T00:00:00.000+01:00 and 2003-02-28T00:00:00.000+01:00
2003-03-01T00:00:00.000+01:00 and 2003-03-31T00:00:00.000+02:00
2003-04-01T00:00:00.000+02:00 and 2003-04-30T00:00:00.000+02:00
2003-05-01T00:00:00.000+02:00 and 2003-05-31T00:00:00.000+02:00
2003-06-01T00:00:00.000+02:00 and 2003-06-30T00:00:00.000+02:00
2003-07-01T00:00:00.000+02:00 and 2003-07-31T00:00:00.000+02:00
2003-08-01T00:00:00.000+02:00 and 2003-08-31T00:00:00.000+02:00
2003-09-01T00:00:00.000+02:00 and 2003-09-30T00:00:00.000+02:00
2003-10-01T00:00:00.000+02:00 and 2003-10-31T00:00:00.000+01:00
2003-11-01T00:00:00.000+01:00 and 2003-11-30T00:00:00.000+01:00
2003-12-01T00:00:00.000+01:00 and 2003-12-31T00:00:00.000+01:00
2004-01-01T00:00:00.000+01:00 and 2004-01-31T00:00:00.000+01:00
2004-02-01T00:00:00.000+01:00 and 2004-02-29T00:00:00.000+01:00
2004-03-01T00:00:00.000+01:00 and 2004-03-31T00:00:00.000+02:00
2004-04-01T00:00:00.000+02:00 and 2004-04-30T00:00:00.000+02:00
2004-05-01T00:00:00.000+02:00 and 2004-05-31T00:00:00.000+02:00
2004-06-01T00:00:00.000+02:00 and 2004-06-30T00:00:00.000+02:00
2004-07-01T00:00:00.000+02:00 and 2004-07-31T00:00:00.000+02:00
2004-08-01T00:00:00.000+02:00 and 2004-08-31T00:00:00.000+02:00
2004-09-01T00:00:00.000+02:00 and 2004-09-30T00:00:00.000+02:00
2004-10-01T00:00:00.000+02:00 and 2004-10-31T00:00:00.000+02:00
2004-11-01T00:00:00.000+01:00 and 2004-11-30T00:00:00.000+01:00
2004-12-01T00:00:00.000+01:00 and 2004-12-31T00:00:00.000+01:00
2005-01-01T00:00:00.000+01:00 and 2005-01-31T00:00:00.000+01:00
2005-02-01T00:00:00.000+01:00 and 2005-02-28T00:00:00.000+01:00
2005-03-01T00:00:00.000+01:00 and 2005-03-31T00:00:00.000+02:00
2005-04-01T00:00:00.000+02:00 and 2005-04-30T00:00:00.000+02:00
2005-05-01T00:00:00.000+02:00 and 2005-05-31T00:00:00.000+02:00
2005-06-01T00:00:00.000+02:00 and 2005-06-30T00:00:00.000+02:00
2005-07-01T00:00:00.000+02:00 and 2005-07-31T00:00:00.000+02:00
2005-08-01T00:00:00.000+02:00 and 2005-08-31T00:00:00.000+02:00
2005-09-01T00:00:00.000+02:00 and 2005-09-30T00:00:00.000+02:00
2005-10-01T00:00:00.000+02:00 and 2005-10-31T00:00:00.000+01:00
2005-11-01T00:00:00.000+01:00 and 2005-11-30T00:00:00.000+01:00
2005-12-01T00:00:00.000+01:00 and 2005-12-31T00:00:00.000+01:00

The split-date-into-months method looks like this:

/**
 * Splits a date range into months. The method provides for each set the
 * start and the end date, so that specific days (1-3-2016 or 5-17-2016) can
 * be covered.
 * 
 * @param from
 *            The implied start-date
 * @param to
 *            The implied end-date
 * @return a collection whit the start and the end of each month laying
 *         between the two days. Also covering the months of the start- and
 *         the end-date itself.
 * @throws IllegalArgumentException
 *             Is thrown when the from-date is later than the to-date.
 */
static Collection<DateTime[]> splitDateIntoMonths(Date from, Date to) throws IllegalArgumentException {

    Collection<DateTime[]> dates = new ArrayList<DateTime[]>();

    DateTime dFrom = new DateTime(from);
    DateTime dTo = new DateTime(to);

    if (dFrom.compareTo(dTo) >= 0) {

        throw new IllegalArgumentException("Provide a to-date greater than the from-date");

    }

    while (dFrom.compareTo(dTo) < 0) {

        DateTime[] dar = new DateTime[2];
        dar[0] = dFrom;
        dar[1] = dFrom
                .withDayOfMonth(dFrom.getMonthOfYear() == dTo.getMonthOfYear() && dFrom.getYear() == dTo.getYear()
                        ? dTo.getDayOfMonth() : dFrom.dayOfMonth().getMaximumValue());

        dates.add(dar);

        dFrom = dFrom.plusMonths(1).withDayOfMonth(1);

    }

    return dates;

}

However, I feel like this could be improved somehow. Are there any major issues which can be improved?

Note: I need to stick to Java 7

Note2: I use Joda-Time

\$\endgroup\$
  • \$\begingroup\$ Are you on Java 8? \$\endgroup\$ – h.j.k. May 17 '16 at 16:16
  • 1
    \$\begingroup\$ @h.j.k. Nope ... sorry forgot to mention :) No lambda for you. \$\endgroup\$ – OddDev May 18 '16 at 5:43
  • 1
    \$\begingroup\$ Is it Joda's DateTime? \$\endgroup\$ – RobAu May 18 '16 at 11:51
  • \$\begingroup\$ @RobAu Yes, will add it to the question. Thanks! \$\endgroup\$ – OddDev May 18 '16 at 12:02
1
\$\begingroup\$

Looks pretty nice overall.

Small bits:

  • I would create a special type for the DateTime[] (as it can have only exactly 2 DateTimes), or reuse an existing one. In joda's case Interval. (If you use Interval, you can also provide a convienence static method that accepts an Interval)
  • Use a access modifier (public) on your method
  • Replace the compareTo with better readable isBefore() and isAfter() and equals() so the reader does not need to know the magic compare values.
  • Your javadoc has an mm-dd-YYYY date format. Your example has dd.mm.YYYY. I would stick to YYYY-mm-dd
|improve this answer|||||
\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.