Adr*_*ins 5 r unidata netcdf netcdf4
我有一个带有时间序列的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" ;
Run Code Online (Sandbox Code Playgroud)
RI内部想要将时间转换为R日期对象.我通过读取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])
Run Code Online (Sandbox Code Playgroud)
这个硬连线解决方案适用于我的具体示例,但我希望R中可能有一个包很好地处理时间单位的UNIDATA netcdf数据约定并将它们安全地转换为R日期对象?
编辑 2023:看来这个包/答案现在已经过时了,请参阅帕特里克接受的答案以获取新的方法。
我刚刚发现(发布问题两年后!)有一个名为ncdf.tools的包,它具有以下功能:
转换日期Ncdf2R
哪个
将 netCDF 文件中的时间向量或自指定原点以来的儒略日(或秒、分钟、小时)向量转换为 POSIXct R 向量。
用法:
convertDateNcdf2R(time.source, units = "days", origin = as.POSIXct("1800-01-01",
tz = "UTC"), time.format = c("%Y-%m-%d", "%Y-%m-%d %H:%M:%S",
"%Y-%m-%d %H:%M", "%Y-%m-%d %Z %H:%M", "%Y-%m-%d %Z %H:%M:%S"))
Run Code Online (Sandbox Code Playgroud)
论据:
time.source
Run Code Online (Sandbox Code Playgroud)
数字向量或 netCDF 连接:自起始点以来的多个时间单位或 netCDF 文件连接,在后一种情况下,时间向量是从 netCDF 文件中提取的,该文件,尤其是时间变量,必须遵循 CF netCDF惯例。
units
Run Code Online (Sandbox Code Playgroud)
字符串:时间源的单位。如果源是 netCDF 文件,则该值将被忽略并从该文件中读取。
origin
Run Code Online (Sandbox Code Playgroud)
POSIXct 对象:时间源的原点或日/小时零。如果源是 netCDF 文件,则该值将被忽略并从该文件中读取。
因此,只需将 netcdf 连接作为第一个参数传递就足够了,函数会处理其余的事情。警告:只有当 netCDF 文件遵循CF 约定时,这才有效(例如,如果您的单位是“自此后的年数”而不是“自此后的秒数”或“自此后的天数”,则它将失败)。
有关该功能的更多详细信息,请访问: https ://rdrr.io/cran/ncdf.tools/man/convertDateNcdf2R.html
您的希望已通过包裹CFtime得到满足。该包可以无缝处理CF元数据约定“时间”维度,包括所有定义的日历。
f1 <- nc_open("file.nc")
cf <- CFtime(f1$dim$time$units, f1$dim$time$calendar, f1$dim$time$vals)
dates <- CFtimestamp(cf)
# This works reliably only for 3 of the 9 defined calendars
dates <- as.Date(dates)
Run Code Online (Sandbox Code Playgroud)
该CFtimestamp()函数为所有可能的日期提供正确的输出,包括“360_day”日历上奇怪的“2023-02-30”,但不包括“2023-03-31”。转换为 POSIXct 很棘手,但您真的需要Date使用 POSIXct 吗?或者字符表示可以很好地工作吗?