我有一个带有时间序列的netcdf文件,时间变量具有以下典型的元数据:
double time(time) ;
time:standard_name = "time" ;
time:bounds = "time_bnds" ;
time:units = "days since 1979-1-1 00:00:00" ;
time:calendar = "standard" ;
time:axis = "T" ;
在R中,我想将时间转换为R date对象。我现在通过阅读units属性并拆分字符串并使用第三个条目作为我的原点(因此假设间距为“days”,时间为00:00等)来实现这一点:
require("ncdf4")
f1<-nc_open("file.nc")
time<-ncvar_get(f1,"time")
tunits<-ncatt_get(f1,"time",attname="units")
tustr<-strsplit(tunits$value, " ")
dates<-as.Date(time,origin=unlist(tustr)[3])
这个硬连线的解决方案适用于我的特定示例,但我希望R中可能有一个包可以很好地处理时间单位的UNIDATA netcdf日期约定,并将它们安全地转换为R日期对象?
4条答案
按热度按时间inn6fuwd1#
编辑2023:似乎这个包/答案现在已经过时了,请参阅帕特里克的accepted answer以获得新的方法。
我刚刚发现(两年后发布的问题!)有一个名为ncdf.tools的软件包,它的功能是:
convertDateNcdf2R
这
将netCDF文件中的时间向量或自指定原点起的儒略日(或秒、分、小时)向量转换为POSIX R向量。
用法:
参数:
数字向量或netCDF连接:在后一种情况下,从netCDF文件中提取时间向量。该文件,尤其是时间变量,必须遵循CF netCDF约定。
字符串:时间源的单位。* 如果源是netCDF文件,则忽略此值并从该文件读取。*
POSIXct对象:时间源的原点或日/小时零点。* 如果源是netCDF文件,则忽略此值并从该文件读取。*
因此,只需将netcdf连接作为第一个参数传递就足够了,函数将处理其余部分。警告:只有当netCDF文件遵循CF conventions(例如,例如,如果你的单位是“years since”而不是“seconds since”或“days since”,它将失败)。
有关该功能的更多详细信息,请访问:https://rdrr.io/cran/ncdf.tools/man/convertDateNcdf2R.html
fslejnso2#
据我所知,没有。我有这个方便的功能使用
lubridate
,这是基本相同的你。编辑:人们可能还想看看
ncdf4.helpers::nc.get.time.series
编辑2:注意,新提出的和目前正在开发的令人敬畏的
stars
包将自动处理日期,请参阅the first blog post的示例。EDIT3:另一种方法是直接使用
units
包,这是stars
使用的。可以这样做:(仍然不能正确处理日历,我不确定units
是否可以)jvidinwx3#
我无法让@AF7的函数处理我的文件,所以我自己写了一个。下面的函数创建了一个POSIXct日期向量,从nc文件中读取开始日期,时间间隔,单位和长度。它适用于许多(但可能不是每一个)形状或形式的nc文件。
编辑
为了解决@AF7的评论所强调的缺陷,即上述代码仅适用于规则间隔的文件,
datev
可以计算为1yjd4xko4#
你的希望已经被package
CFtime
满足了。这个包可以无缝地处理CF元数据约定的“时间”维度,包括所有定义的日历。CFtimestamp()
函数为所有可能的日期提供正确的输出,包括“360_day”日历上的奇数“2023-02-30”,但不包括“2023-03-31”。转换为POSIXct是很棘手的,但是你真的需要一个Date
来工作吗?或者一个字符表示就可以了?