install.packages(c("terra", "ncdf4", "ncdf4.helpers", "PCICt",
"dplyr", "magrittr"))
# load packages
library(terra)
library(ncdf4)
library(ncdf4.helpers)
library(PCICt)
library(dplyr)
library(magrittr)
# List of pacakges that we will use
<- c("terra", "ncdf4", "ncdf4.helpers", "PCICt", "dplyr", "magrittr")
list.of.packages # If is not installed, install the pacakge
<- list.of.packages[!(list.of.packages %in% installed.packages()[,"Package"])]
new.packages if(length(new.packages)) install.packages(new.packages)
# Load packages
lapply(list.of.packages, require, character.only = TRUE)
5 netCDF files in R: Raster, Spatial objects
The aim of this tutorial is to provide a worked example (i.e., a function) of how to transform a regridded netCDF into a Raster object using R.
5.1 Data import
Load the required packages.
5.2 Function to transform netCDF files into Raster objects
You can read netCDF using raster::stack
or the terra::rast
functions from the raster
and terra
packages. However, this code allows more control over the outputs.
# NO GUARANTEES THAT CODE IS CORRECT
# Caveat Emptor! (Latin for "Let the buyer beware")
# Define generalities
= "data/tos_Omon_GFDL-ESM4_ssp585_r1i1p1f1_gr_201501-203412.nc"
nc = "tos"
v = "lon"
x = "lat"
y # Working with netCDF file
<- ncdf4::nc_open(nc)
nc <- ncdf4::ncvar_get(nc, v) # x, y, year
dat <- dat
dat[] <- ncdf4::ncvar_get(nc, varid = x) %>%
rlon range()
<- ncdf4::ncvar_get(nc, varid = y) %>%
rlat range()
<- dim(dat)[1] # nolint
X <- dim(dat)[2] # nolint
Y <- ncdf4.helpers::nc.get.time.series(nc,
tt v = "time",
time.dim.name = "time")
<- as.POSIXct(tt)
tt <- as.Date(tt)
tt ::nc_close(nc)
ncdf4# Make a raster with the right dims to fill with lat&lon
<- terra::rast(nrow = Y, ncol = X, extent = terra::ext(c(rlon, rlat)))
rs # Fix orientation of original data
# [and then create a raster with this fix orientation]
<- terra::xyFromCell(rs, 1:terra::ncell(rs)) %>%
drs as_tibble()
# Create raster stacks of depths for every month
<- list() # to allocate results # nolint
rs_list <- terra::rast()
st for (i in 1:length(tt)) { # nolint
<- dplyr::bind_cols(drs,
dt1 as.vector(dat[, , i])) %>%
::set_colnames(c("x", "y", v))
magrittr<- terra::rast(dt1, type = "xyz")
dt1 names(dt1) <- tt[i]
<- c(st, terra::flip(dt1))
st print(paste0(tt[i], " of ", length(tt)))
}
5.3 Crop/Manipulate and project
# The Mozambique Channel
<- terra::crop(st, terra::ext(c(30, 75, -35, -7)))
st ::crs(st) <- "+proj=longlat +datum=WGS84 +ellps=WGS84 +towgs84=0,0,0"
terra# One plot to check
plot(st, 1)
5.4 Save the Raster file
# Writing Raster
::writeRaster(st,
terra"tos_Omon_GFDL-ESM4_ssp585_r1i1p1f1_gr_201501-203412.tif",
overwrite = TRUE,
filetype = "GTiff")