Sunday seemed to be a good day to update R
from version 4.2.3 to 4.3.2 (on Win 10) to start with something up-to-date into a new week.
I was using the zoo
package for some time series writing to basic text files for saving data. This worked for years, but after the above upgrade I encountered a change in the output where suddenly midnight times are left out:
Code to test (using zoo
version 1.8.12):
library(zoo)
write.zoo(
zoo(
c(46, 47),
c(as.POSIXct("2023-11-26 00:00:00"), as.POSIXct("2023-11-26 01:00:00"))
)
)
With R prior to 4.3.0 the result looks like:
"2023-11-26 00:00:00" 46
"2023-11-26 01:00:00" 47
But starting with 4.3.0 it changed to:
"2023-11-26" 46
"2023-11-26 01:00:00" 47
As documentation of zoo
says that write.zoo()
is a convenience function for write.table()
I tried to substitute with this getting proper results (with midnight timestamps) again:
write.table(
zoo(
c(46, 47),
c(as.POSIXct("2023-11-26 00:00:00"), as.POSIXct("2023-11-26 01:00:00"))
)
)
outputs
"2023-11-26 00:00:00" 46
"2023-11-26 01:00:00" 47
under any mentioned version of R
.
So it seems like the write.zoo
function has been broken by R >= 4.3.0, but the story continues...
As one can see in zoo
sources this function is rather simple and produces a data.frame
from the zoo object by copying the index while using as.character()
.
Testing again this very simple call on POSIXct objects
R <4.3.0:
> as.character(c(as.POSIXct("2023-11-26 00:00:00"), as.POSIXct("2023-11-26 01:00:00")))
[1] "2023-11-26 00:00:00" "2023-11-26 01:00:00"
R >=4.3.0:
> as.character(c(as.POSIXct("2023-11-26 00:00:00"), as.POSIXct("2023-11-26 01:00:00")))
[1] "2023-11-26" "2023-11-26 01:00:00"
tells me, that this might be the reason for failure of write.zoo()
Now I'm puzzled because that is very basic R-functionality which was not mentioned to be changing in the R News. The output also looks awkward - why should there be two different formats be produced?
There is another question on R write.table remove 0:00:00 from Timestamps which uses write.table()
directly on data.frame
(so no zoo
here) and yields the same results also in my case:
> write.table(data.frame(Index = c(as.POSIXct("2023-11-26 00:00:00"), as.POSIXct("2023-11-26 01:00:00")), Value = c(46, 47)), row.names = FALSE)
"Index" "Value"
2023-11-26 46
2023-11-26 01:00:00 47
So obviously my "workaround" by using write.table()
on zoo
objects only works because those objects are different internally. Unfortunately is beyond my understanding of R
as well as if the as.character()
behavior is intended and useful.
Any further explanation from the community on this?
Thanks for reporting this problem. As others have already pointed out in the comments, the issue was triggered by a change in behavior of as.character()
for POSIXt
object.
I have just committed an update to write.zoo()
on R-Forge which now uses format(index(x))
rather than the old as.character(index(x))
(which never was an ideal choice to begin with).
The update can be installed from R-Forge via
install.packages("zoo", repos="https://R-Forge.R-project.org")