Select MOD (RUNC (MONTHS_BETWEEN (TO_DATE (\'28-Mar-2017\', \'DD-MON-YYYY\'),
TO_DATE (\'28-Feb-2017\', \'DD-MON-YYYY\'))), 12) Months from dual
Why i
Because it is working to its documented specification:
MONTHS_BETWEEN
returns number of months between datesdate1
anddate2
. The month and the last day of the month are defined by the parameterNLS_CALENDAR
. Ifdate1
is later thandate2
, then the result is positive. Ifdate1
is earlier thandate2
, then the result is negative. Ifdate1
anddate2
are either the same days of the month or both last days of months, then the result is always an integer. Otherwise Oracle Database calculates the fractional portion of the result based on a 31-day month and considers the difference in time componentsdate1
anddate2
.
If you have requirements that are different to this then you will need to write your own function.
You are wrong. MONTHS_BETWEEN
treats the time span from date '2017-02-28'
to date '2017-03-28'
as exactly one month (same day in two adjacent months). This can be read in the docs: https://docs.oracle.com/cd/B19306_01/server.102/b14200/functions089.htm
MONTHS_BETWEEN returns number of months between dates date1 and date2. If date1 is later than date2, then the result is positive. If date1 is earlier than date2, then the result is negative. If date1 and date2 are either the same days of the month or both last days of months, then the result is always an integer. Otherwise Oracle Database calculates the fractional portion of the result based on a 31-day month and considers the difference in time components date1 and date2.
One date is bigger than the other so you get a positive or negative number (i.e. not zero) depending on which is first and which is second parameter, and as the days equal, the result will be an integer. That is 1 or -1 for adjacent months.
Month calculation is a strange thing anyway, as a month is not a defined time span. You seem to have a certain definition in mind, which simply is different from how MONTHS_BETWEEN
defines it. Nothing wrong about that. I would agree with MONTHS_BETWEEN
in this case; from Feb 28 to Mar 28 is "exactly" one month. If you want different rules, then apply your own math :-)