使用xarray改变坐标系以便Slice操作
Using xarray to change coordinate system in order to Slice operation
我是新来的。
首先,我非常感谢您的时间和考虑。
关于在 python 中管理 2 个不同的 netcdf 文件,我有 2 个问题。
我搜索了很多,但不幸的是我找不到解决方案。
1- 我有一个 netcdf 文件,其坐标如下:
time datetime64[ns] 2016-08-16T22:00:00
* y (y) int32 220000 ... 620000
* x (x) int32 20000 ... 720000
lat (y, x) float64 dask.array<shape=(401, 701),
lon (y, x) float64 dask.array<shape=(401, 701),
我需要将坐标更改为 lon/lat,以便我可以根据特定的 lon/lat 坐标(通过使用 xarray)对区域进行切片。但我不知道如何将 x 和 y 更改为 lon lat。
这是我的代码:
import xarray as xr
import matplotlib.pyplot as plt
p = "R_201608.nc"
ds = xr.open_mfdataset(p)
q=ds.RR.sel(time='2016-08-16T21:00:00')
2- 与 1 类似,我有另一个 netcdf 文件,其坐标如下:
* X (X) float32 557600.0 .. 579400.0
* Y (Y) float32 5190600 ... 5205400.0
* time (time) datetime64[ns] 2007-01I
如何将 x 和 y 转换为 lon/lat 系统,以便我可以在 lon/lat 系统中绘制它?
与@Ryan 相关的编辑:
1- 是的。此文件显示大面积降雨。我想把它切成更小的区域——与 q2 相关的文件的类似区域——并使用偏差、RMSE 等对它们进行比较。这里是与该文件相关的完整信息:
<xarray.Dataset>
Dimensions: (time: 2976, x: 701, y: 401)
Coordinates:
* time (time) datetime64[ns] 2016-08-31T23:45:00
* y (y) int32 220000 221000 ... 619000 620000
* x (x) int32 20000 21000 ... 719000 720000
lat (y, x) float64 dask.array<shape=(401, 701),chunksize=(401, 701)>
lon (y, x) float64 dask.array<shape=(401, 701), chunksize=(401, 701)
Data variables:
RR (time, y, x) float32 dask.array<shape=(2976, 401, 701), chunksize=(2976, 401, 701)>
lambert_conformal_conic int32 ...
Conventions: CF-1.5
与@Ryan 相关的编辑:2- 这里是关于第二个文件(较小区域)的完整信息:
<xarray.DataArray 'Precip' (time: 8928, Y: 75, X: 110)>
dask.array<shape=(8928, 75, 110), dtype=float32, chunksize=(288, 75, 110)>
Coordinates:
sensor_height_precip float32 1.5
sensor_height_P float32 1.5
* X (X) float32 557600.0 557800.0 ... 579200.0 579400.0
* Y (Y) float32 5190600.0 5190800.0 ... 5205400.0
* time (time) datetime64[ns] 2007-01-31T23:55:00
Attributes:
grid_mapping: UTM33N
ancillary_variables: QFlag_Precip QGrid_Precip
long_name: Precipitation Amount
standard_name: precipitation_amount
cell_methods: time:sum
units: mm
问题1)中,lon和lat是二维的(都有x,y维度),无法将lon和lat转换为维度坐标。维度坐标,用于切片,只能是一维的。如果您可以更具体地说明切片后要做什么,我们可以提供更多有关如何进行的建议。您是否要 select 特定的纬度/经度范围,然后计算一些统计数据(例如均值/方差)?
在问题 2) 中,您似乎有地图投影。没有关于投影的更多信息,就不可能转换为纬度/经度坐标或在地图上绘制。您的数据集中是否包含有关所用地图投影的更多信息?你能 post print(ds)
的完整输出吗?
在你的帮助下我已经解决了我的问题。非常感谢。
如@Bart 所述,我可以使用 PYPROJ 将两个数据集的坐标更改为 lon/lat。从原始坐标和投影坐标创建 meshgid 是关键点。
from pyproj import Proj
nxv, nyv = np.meshgrid(nx, ny)
unausp = Proj('+proj=lcc +lat_1=49 +lat_2=46 +lat_0=47.5 +lon_0=13.33333333333333 +x_0=400000 +y_0=400000 +ellps=bessel +towgs84=577.326,90.129,463.919,5.137,1.474,5.297,2.4232 +units=m +no_defs ')
nlons, nlats = unausp(nxv, nyv, inverse=True)
upLon, upLat = np.meshgrid(nlons,nlats)
由于我想比较两个具有不同空间分辨率(不同网格大小)的降雨数据集,我必须使用 xarray 插值对其中一个进行放大:
upnew_lon = np.linspace(w.X[0], w.X[-1], w.dims['X'] // 5)
upnew_lat = np.linspace(w.Y[0], w.Y[-1], w.dims['Y'] //5)
uppds = w.interp(Y=upnew_lat, X=upnew_lon)
据我所知,这个插值是基于线性插值的。我将放大的数据集与原始数据集进行了比较。升级后平均降雨量减少约 0.03 毫米/天。我只想知道你认为这种sub-hourly降雨量的放大方法可靠吗?
我是新来的。 首先,我非常感谢您的时间和考虑。 关于在 python 中管理 2 个不同的 netcdf 文件,我有 2 个问题。 我搜索了很多,但不幸的是我找不到解决方案。
1- 我有一个 netcdf 文件,其坐标如下:
time datetime64[ns] 2016-08-16T22:00:00
* y (y) int32 220000 ... 620000
* x (x) int32 20000 ... 720000
lat (y, x) float64 dask.array<shape=(401, 701),
lon (y, x) float64 dask.array<shape=(401, 701),
我需要将坐标更改为 lon/lat,以便我可以根据特定的 lon/lat 坐标(通过使用 xarray)对区域进行切片。但我不知道如何将 x 和 y 更改为 lon lat。 这是我的代码:
import xarray as xr
import matplotlib.pyplot as plt
p = "R_201608.nc"
ds = xr.open_mfdataset(p)
q=ds.RR.sel(time='2016-08-16T21:00:00')
2- 与 1 类似,我有另一个 netcdf 文件,其坐标如下:
* X (X) float32 557600.0 .. 579400.0
* Y (Y) float32 5190600 ... 5205400.0
* time (time) datetime64[ns] 2007-01I
如何将 x 和 y 转换为 lon/lat 系统,以便我可以在 lon/lat 系统中绘制它?
与@Ryan 相关的编辑: 1- 是的。此文件显示大面积降雨。我想把它切成更小的区域——与 q2 相关的文件的类似区域——并使用偏差、RMSE 等对它们进行比较。这里是与该文件相关的完整信息:
<xarray.Dataset>
Dimensions: (time: 2976, x: 701, y: 401)
Coordinates:
* time (time) datetime64[ns] 2016-08-31T23:45:00
* y (y) int32 220000 221000 ... 619000 620000
* x (x) int32 20000 21000 ... 719000 720000
lat (y, x) float64 dask.array<shape=(401, 701),chunksize=(401, 701)>
lon (y, x) float64 dask.array<shape=(401, 701), chunksize=(401, 701)
Data variables:
RR (time, y, x) float32 dask.array<shape=(2976, 401, 701), chunksize=(2976, 401, 701)>
lambert_conformal_conic int32 ...
Conventions: CF-1.5
与@Ryan 相关的编辑:2- 这里是关于第二个文件(较小区域)的完整信息:
<xarray.DataArray 'Precip' (time: 8928, Y: 75, X: 110)>
dask.array<shape=(8928, 75, 110), dtype=float32, chunksize=(288, 75, 110)>
Coordinates:
sensor_height_precip float32 1.5
sensor_height_P float32 1.5
* X (X) float32 557600.0 557800.0 ... 579200.0 579400.0
* Y (Y) float32 5190600.0 5190800.0 ... 5205400.0
* time (time) datetime64[ns] 2007-01-31T23:55:00
Attributes:
grid_mapping: UTM33N
ancillary_variables: QFlag_Precip QGrid_Precip
long_name: Precipitation Amount
standard_name: precipitation_amount
cell_methods: time:sum
units: mm
问题1)中,lon和lat是二维的(都有x,y维度),无法将lon和lat转换为维度坐标。维度坐标,用于切片,只能是一维的。如果您可以更具体地说明切片后要做什么,我们可以提供更多有关如何进行的建议。您是否要 select 特定的纬度/经度范围,然后计算一些统计数据(例如均值/方差)?
在问题 2) 中,您似乎有地图投影。没有关于投影的更多信息,就不可能转换为纬度/经度坐标或在地图上绘制。您的数据集中是否包含有关所用地图投影的更多信息?你能 post print(ds)
的完整输出吗?
在你的帮助下我已经解决了我的问题。非常感谢。 如@Bart 所述,我可以使用 PYPROJ 将两个数据集的坐标更改为 lon/lat。从原始坐标和投影坐标创建 meshgid 是关键点。
from pyproj import Proj
nxv, nyv = np.meshgrid(nx, ny)
unausp = Proj('+proj=lcc +lat_1=49 +lat_2=46 +lat_0=47.5 +lon_0=13.33333333333333 +x_0=400000 +y_0=400000 +ellps=bessel +towgs84=577.326,90.129,463.919,5.137,1.474,5.297,2.4232 +units=m +no_defs ')
nlons, nlats = unausp(nxv, nyv, inverse=True)
upLon, upLat = np.meshgrid(nlons,nlats)
由于我想比较两个具有不同空间分辨率(不同网格大小)的降雨数据集,我必须使用 xarray 插值对其中一个进行放大:
upnew_lon = np.linspace(w.X[0], w.X[-1], w.dims['X'] // 5)
upnew_lat = np.linspace(w.Y[0], w.Y[-1], w.dims['Y'] //5)
uppds = w.interp(Y=upnew_lat, X=upnew_lon)
据我所知,这个插值是基于线性插值的。我将放大的数据集与原始数据集进行了比较。升级后平均降雨量减少约 0.03 毫米/天。我只想知道你认为这种sub-hourly降雨量的放大方法可靠吗?