问题
I have a script in which I subset my data according to some set time periods and wanted to subset all the records that had occurred in the last month.
However if I try to subtract one month from today's date it yields an NA:
> today <- Sys.Date()
> today
[1] "2017-03-29"
> today - months(1)
[1] NA
I do have lubridate loaded but I think this calculation is being performed with base R. If I subtract 2 or more months it works fine:
> today - months(2)
[1] "2017-01-29"
> today - months(3)
[1] "2016-12-29"
Does anyone have any ideas about what might be going on?
UPDATE: I think this is something to do with simple date subtraction not handling leap year cases (2017 is not a leap year so "2017-02-29"
does not exist).
Are there other packages / functions that take into account leap years? For the above example I would expect the answer to revert to the last day of the previous month, i.e.:
today - months(1)
# Should yield:
"2017-02-28"
Would it make sense for this calculation to give the same results for both today and yesterday (or what is the ISO convention for this)?
> sessionInfo()
R version 3.3.2 (2016-10-31)
Platform: x86_64-w64-mingw32/x64 (64-bit)
Running under: Windows 7 x64 (build 7601) Service Pack 1
locale:
[1] LC_COLLATE=English_United Kingdom.1252 LC_CTYPE=English_United Kingdom.1252
[3] LC_MONETARY=English_United Kingdom.1252 LC_NUMERIC=C
[5] LC_TIME=English_United Kingdom.1252
attached base packages:
[1] stats graphics grDevices utils datasets methods base
other attached packages:
[1] xlsx_0.5.7 xlsxjars_0.6.1 rJava_0.9-8 MRAtools_0.6.8 stringdist_0.9.4.4 stringr_1.2.0
[7] stringi_1.1.3 lubridate_1.6.0 data.table_1.10.4 PKI_0.1-3 base64enc_0.1-3 digest_0.6.12
[13] getPass_0.1-1 RPostgreSQL_0.5-1 DBI_0.5-1
loaded via a namespace (and not attached):
[1] magrittr_1.5 rstudioapi_0.6 tools_3.3.2 parallel_3.3.2
回答1:
The calculation of months is indeed perfomed by base R but not the way your think. Months is used to get the month of a date object.
#Example
today <- Sys.Date()
months(today)
[1] "March"
To add or substract months, you should use %m+%
from lubridate
:
today <- Sys.Date()
today %m+% months(-1)
[1] "2017-02-28"
回答2:
One month ago is non-defined in this context. February 29th only exists in leap years.
See the lubridate documentation:
Note: Arithmetic with periods can results in undefined behavior when non-existent dates are involved (such as February 29th in non-leap years). Please see Period-class for more details and %m+% and add_with_rollback for alternative operations.
The lubridate
package can handle what you are doing, but you need to perform the operaton using %m+%
.
来源:https://stackoverflow.com/questions/43098932/r-subtracting-1-month-from-todays-date-gives-na