2

I have this method that returns me a Date() changed by one of it's "fields" (DAY, MONTH, YEAR).

public static Date getDateChanged(Date date, int field, int value) {
    Calendar cal = Calendar.getInstance();
    cal.setTime(date);
    cal.set(field, value);
    return cal.getTime();
}

However, cal.set() is unable to give an exception when the field we are trying to set is not compatible with the date in question. So, in this case:

Date date = new Date();
date = getDateChanged(date, Calendar.DAY_OF_MONTH, 29); 
date = getDateChanged(date, Calendar.MONTH, 1); // feb

date is, in the end, 01/03/15, because Calendar.set() detects that February can't be set with day 29, so automatically set's date to the next possible day (I thinks this is how the routine works).

This is not so bad, however, in my case,

I want to detect that the date I'm trying to build is impossible and then start decrementing the day, so in this case what I'm trying to achieve is 28/02/15, how can I do this?

Example:

29/02/15 ===> 28/02/15

VedantK
  • 9,728
  • 7
  • 66
  • 71
yat0
  • 967
  • 1
  • 13
  • 29

4 Answers4

2

You can use cal.getActualMaximum(Calendar.DAY_OF_MONTH) to find the maximum days in the given month for your calendar instance.

This way, you can handle the case you mentioned above yourself.

Also see the answer here: Number of days in particular month of particular year?

Community
  • 1
  • 1
zerga
  • 68
  • 1
  • 5
2

You can use:

public void setLenient(boolean lenient)

Specifies whether or not date/time interpretation is to be lenient. With lenient interpretation, a date such as "February 942, 1996" will be treated as being equivalent to the 941st day after February 1, 1996. With strict (non-lenient) interpretation, such dates will cause an exception to be thrown. The default is lenient.

Parameters:
    lenient - true if the lenient mode is to be turned on; false if it is to be turned off.
See Also:
    isLenient(), DateFormat.setLenient(boolean)

This way you get exception when you pass something wrong :)

ap0calypt1c
  • 481
  • 4
  • 10
  • i think he don't want exception – VedantK Jul 30 '15 at 09:02
  • He said: 'I want to detect that the date I'm trying to build is impossible and then start decrementing the day'. Throwing exception is one way to determine that something is impossible. Also he can catch it and do something else based on this. – ap0calypt1c Jul 30 '15 at 09:05
  • now date if not exceptable(here 29/2/15) gets added as (01/03/15) to next date, but here he want 28/2/15 to be added. @polska please correct me if i am wrong – VedantK Jul 30 '15 at 09:08
  • well if he puts the flag with false it will get exception. Then he can decrease the number by one and try again or do something else which will end up in the putting correct date. – ap0calypt1c Jul 30 '15 at 09:14
1

You can check the maximum value with getActualMaximum:

public static Date getDateChanged(Date date, int field, int value) {
    Calendar cal = Calendar.getInstance();
    cal.setTime(date);
    int maximum = calendar.getActualMaximum(field);
    if (value > maximum) {
        value = maximum;
    }
    cal.set(field, value);
    return cal.getTime();
}
Glorfindel
  • 21,988
  • 13
  • 81
  • 109
0

May be this solution will help you

public static Date getDateChanged(Date date, int field, int value) {
    Calendar cal = Calendar.getInstance();
    cal.setTime(date);
    cal.set(field, value);
    if (field == Calendar.MONTH && cal.get(Calendar.MONTH) != value) {
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(date);
        int month = (cal.get(Calendar.MONTH) - 1) < 0 ? 0 : (cal.get(Calendar.MONTH) - 1);
        calendar.set(Calendar.DATE, calendar.getActualMinimum(Calendar.DATE));
        calendar.set(Calendar.MONTH, month);
        calendar.set(Calendar.DATE, calendar.getActualMaximum(Calendar.DATE));
        return calendar.getTime();
    }
    return cal.getTime();
}
Albin
  • 1,929
  • 2
  • 14
  • 18