1616import rasterio as rio
1717import xarray as xr
1818
19+ from .gis import CRS , _as_transform
20+
1921logger = logging .getLogger (__name__ )
2022
2123
@@ -137,50 +139,40 @@ def calculate_windspeed_bias_correction(
137139 real_average : str | rio .DatasetReader ,
138140 height : int = 100 ,
139141 data_average : xr .DataArray | None = None ,
140- ):
142+ data_crs : CRS | str | int | None = None ,
143+ ) -> xr .DataArray :
141144 """
142145 Derive a bias correction factor for windspeed at lra_height
143146
144147 Regrids the raster dataset in real_average to cutout grid, retrieves the average
145148 windspeed from the first dataset that offers
146- :py:func:`retrieve_longrunaverage_windspeed ` (only ERA5, currently).
149+ :py:func:`retrieve_windspeed_average ` (only ERA5, currently).
147150
148151 Parameters
149152 ----------
150- cutout : Cutout
151- Atlite cutout
153+ cutout : Cutout, optional
154+ Cutout for which to retrieve data_average. Can be omitted if
155+ data_average and data_crs are passed explicitly.
152156 real_average : Path or rasterio.Dataset
153157 Raster dataset with wind speeds to bias correct average wind speeds
154158 height : int
155159 Height in meters at which average windspeeds are provided
156160 data_average : DataArray, optional
157- Long run average of the windspeed data, if not provided it is retrieved.
161+ Long run average of the windspeed data, if not provided it is retrieved
162+ with the standard settings suitable for bias correction with GWA 3.1.
163+ data_crs : CRS like, optional
164+ CRS that data_average is given in.
158165
159166 Returns
160167 -------
161168 DataArray
162169 Ratio between windspeeds in `real_average` to those of average windspeeds in
163170 dataset.
164- """
165- if isinstance (real_average , str | Path ):
166- real_average = rio .open (real_average )
167171
168- if isinstance (real_average , rio .DatasetReader ):
169- real_average = rio .band (real_average , 1 )
170-
171- if isinstance (real_average , rio .Band ):
172- real_average , transform = rio .warp .reproject (
173- real_average ,
174- np .empty (cutout .shape ),
175- dst_crs = cutout .crs ,
176- dst_transform = cutout .transform ,
177- dst_nodata = np .nan ,
178- resampling = rio .enums .Resampling .average ,
179- )
180-
181- real_average = xr .DataArray (
182- real_average , [cutout .coords ["y" ], cutout .coords ["x" ]]
183- )
172+ See Also
173+ --------
174+ atlite.datasets.era5.retrieve_windspeed_average
175+ """
184176
185177 if data_average is None :
186178 from . import datasets
@@ -190,6 +182,7 @@ def calculate_windspeed_bias_correction(
190182 getattr (datasets , module ), "retrieve_windspeed_average"
191183 )
192184 if retrieve_windspeed_average is not None :
185+ data_crs = getattr (datasets , module ).crs
193186 break
194187 else :
195188 raise AssertionError (
@@ -201,6 +194,31 @@ def calculate_windspeed_bias_correction(
201194 )
202195 data_average = retrieve_windspeed_average (cutout , height )
203196
197+ if isinstance (real_average , str | Path ):
198+ real_average = rio .open (real_average )
199+
200+ if isinstance (real_average , rio .DatasetReader ):
201+ real_average = rio .band (real_average , 1 )
202+
203+ if isinstance (real_average , rio .Band ):
204+ transform = _as_transform (data_average .indexes ["x" ], data_average .indexes ["y" ])
205+
206+ real_average , _ = rio .warp .reproject (
207+ real_average ,
208+ np .empty (data_average .shape ),
209+ dst_crs = CRS (data_crs ),
210+ dst_transform = transform ,
211+ dst_nodata = np .nan ,
212+ resampling = rio .enums .Resampling .average ,
213+ )
214+
215+ real_average = xr .DataArray (real_average , data_average .coords )
216+ else :
217+ raise ValueError (
218+ f"`real_average` needs to be a path or rasterio object to a raster dataset"
219+ f", but is: { real_average } "
220+ )
221+
204222 return (real_average / data_average ).assign_attrs (height = height )
205223
206224
0 commit comments