Skip to content

Commit 5a1c9af

Browse files
committed
remove optional reduction application from regroup
1 parent 842bbb3 commit 5a1c9af

File tree

2 files changed

+109
-52
lines changed

2 files changed

+109
-52
lines changed

enacts/calc.py

Lines changed: 5 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1052,9 +1052,8 @@ def resample_interval_to_daily(time_series, is_intensive=None, time_dim="T_bins"
10521052
return time_series
10531053

10541054

1055-
def regroup(time_series, group="1D", method=None, method_kwargs={}, time_dim="T"):
1056-
""" Regroup any type of interval-based time series to another,
1057-
according to `method`
1055+
def regroup(time_series, group="1D", time_dim="T"):
1056+
""" Regroup any type of interval-based time series to another
10581057
10591058
Parameters
10601059
----------
@@ -1066,21 +1065,13 @@ def regroup(time_series, group="1D", method=None, method_kwargs={}, time_dim="T"
10661065
or d Mmm - d Mmm. See Notes for details.
10671066
As integer or array-like[pandas.DatetimeIndex],
10681067
see xr.DataArray.groupby_bins' `bins` Parameter
1069-
method: str, optional
1070-
name of xr.core.groupby.DataArrayGroupBy's Method to apply to form the new
1071-
intervals. Default is None in which case no final reduction is applied
1072-
and returned `time_series` is a xr.core.groupby.DataArrayGroupBy object of
1073-
days grouped according to `group` .
1074-
method_kwargs: dict, optional
1075-
keyword arguments of `method` . Default is an empty dict in which case
1076-
default keywords of `method` will be applied.
10771068
time_dim : str, optional
10781069
name of interval time dimenstion, default is "T"
10791070
10801071
Returns
10811072
-------
1082-
regrouped : xr.DataArray or xr.Dataset
1083-
`time_series` regrouped to specified time intervals according to `method`
1073+
regrouped : xr.core.groupby.DataArray/DatasetGroupBy
1074+
`time_series` grouped to specified time intervals groups
10841075
10851076
See Also
10861077
--------
@@ -1233,10 +1224,7 @@ def regroup(time_series, group="1D", method=None, method_kwargs={}, time_dim="T"
12331224
assert (bins.size > 1), (
12341225
"data must span at least one full group (need 2 edges to form 1 bin)"
12351226
)
1236-
regrouped = time_series.groupby_bins(time_series[time_dim], bins, right=False)
1237-
if method is not None :
1238-
regrouped = getattr(regrouped, method)(**method_kwargs)
1239-
return regrouped
1227+
return time_series.groupby_bins(time_series[time_dim], bins, right=False)
12401228

12411229

12421230
def strftimeb2int(strftimeb):

enacts/tests/test_calc.py

Lines changed: 104 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -105,7 +105,7 @@ def test_regroup_daily_to_7D():
105105
t = pd.date_range(start="2000-01-01", end="2000-01-28", freq="1D")
106106
values = 1 + np.arange(t.size)
107107
precip = xr.DataArray(values, coords={"T": t})
108-
precip_int = calc.regroup(precip, group="7D", method="sum")
108+
precip_int = calc.regroup(precip, group="7D").sum()
109109

110110
np.testing.assert_array_equal(
111111
precip_int, precip.resample(T="7D").sum(skipna=True, min_count=7).dropna("T")
@@ -121,8 +121,8 @@ def test_regroup_daily_to_pentad():
121121
values_leap = 1 + np.arange(t_leap.size)
122122
precip = xr.DataArray(values, coords={"T": t})
123123
precip_leap = xr.DataArray(values_leap, coords={"T": t_leap})
124-
precip_pentad = calc.regroup(precip, group="pentad", method="sum")
125-
precip_pentad_leap = calc.regroup(precip_leap, group="pentad", method="sum")
124+
precip_pentad = calc.regroup(precip, group="pentad").sum()
125+
precip_pentad_leap = calc.regroup(precip_leap, group="pentad").sum()
126126

127127
np.testing.assert_array_equal(precip_pentad.data, [
128128
15., 40., 65., 90., 115., 140., 165., 190., 215., 240., 265.,
@@ -141,7 +141,7 @@ def test_regroup_daily_to_8day():
141141
t = pd.date_range(start="2020-11-01T120000", end="2021-02-01T120000", freq="1D")
142142
values = 1 + np.arange(t.size)
143143
precip = xr.DataArray(values, coords={"T": t})
144-
precip_8day = calc.regroup(precip, group="8day", method="sum")
144+
precip_8day = calc.regroup(precip, group="8day").sum()
145145

146146
np.testing.assert_array_equal(precip_8day.data, [
147147
92., 156., 220., 284., 348., 412., 351., 524., 588., 652., 716.
@@ -152,7 +152,7 @@ def test_regroup_daily_to_dekad():
152152
t = pd.date_range(start="2020-01-01T120000", end="2020-03-09T120000", freq="1D")
153153
values = 1 + np.arange(t.size)
154154
precip = xr.DataArray(values, coords={"T": t})
155-
precip_dekad = calc.regroup(precip, group="dekad", method="sum")
155+
precip_dekad = calc.regroup(precip, group="dekad").sum()
156156

157157
np.testing.assert_array_equal(
158158
precip_dekad.data, [55., 155., 286., 365., 465., 504.]
@@ -163,7 +163,7 @@ def test_regroup_daily_to_16day():
163163
t = pd.date_range(start="2000-11-01T120000", end="2001-02-01T120000", freq="1D")
164164
values = 1 + np.arange(t.size)
165165
precip = xr.DataArray(values, coords={"T": t})
166-
precip_16day = calc.regroup(precip, group="16day", method="sum")
166+
precip_16day = calc.regroup(precip, group="16day").sum()
167167

168168
np.testing.assert_array_equal(
169169
precip_16day.data, [376., 632., 763., 1112., 1368.]
@@ -174,7 +174,7 @@ def test_regroup_daily_to_1M():
174174
t = pd.date_range(start="2000-11-01T120000", end="2001-02-01T120000", freq="1D")
175175
values = 1 + np.arange(t.size)
176176
precip = xr.DataArray(values, coords={"T": t})
177-
precip_month = calc.regroup(precip, group="1M", method="sum")
177+
precip_month = calc.regroup(precip, group="1M").sum()
178178

179179
np.testing.assert_array_equal(
180180
precip_month.data,
@@ -186,7 +186,7 @@ def test_regroup_daily_to_5M():
186186
t = pd.date_range(start="2000-01-01", end="2001-12-31", freq="1D")
187187
values = 1 + np.arange(t.size)
188188
precip = xr.DataArray(values, coords={"T": t})
189-
precip_month = calc.regroup(precip, group="5M", method="sum")
189+
precip_month = calc.regroup(precip, group="5M").sum()
190190

191191
xr.testing.assert_equal(
192192
precip_month.isel(T_bins=0, drop=True),
@@ -202,7 +202,7 @@ def test_regroup_daily_to_season1():
202202
t = pd.date_range(start="2000-01-01", end="2002-12-31", freq="1D")
203203
values = 1 + np.arange(t.size)
204204
precip = xr.DataArray(values, coords={"T": t})
205-
precip_seas = calc.regroup(precip, group="14 Dec - 29 Mar", method="sum")
205+
precip_seas = calc.regroup(precip, group="14 Dec - 29 Mar").sum()
206206

207207
xr.testing.assert_equal(
208208
precip_seas.isel(T_bins=0, drop=True),
@@ -230,7 +230,7 @@ def test_regroup_daily_to_season2():
230230
t = pd.date_range(start="2000-01-01", end="2001-12-31", freq="1D")
231231
values = 1 + np.arange(t.size)
232232
precip = xr.DataArray(values, coords={"T": t})
233-
precip_seas = calc.regroup(precip, group="19-29 Feb", method="sum")
233+
precip_seas = calc.regroup(precip, group="19-29 Feb").sum()
234234

235235
xr.testing.assert_equal(
236236
precip_seas.isel(T_bins=0, drop=True),
@@ -246,7 +246,7 @@ def test_regroup_daily_to_season3():
246246
t = pd.date_range(start="2000-01-01", end="2001-12-31", freq="1D")
247247
values = 1 + np.arange(t.size)
248248
precip = xr.DataArray(values, coords={"T": t})
249-
precip_seas = calc.regroup(precip, group="29 Feb - 29 Mar", method="sum")
249+
precip_seas = calc.regroup(precip, group="29 Feb - 29 Mar").sum()
250250

251251
xr.testing.assert_equal(
252252
precip_seas.isel(T_bins=0, drop=True),
@@ -262,7 +262,7 @@ def test_regroup_daily_to_int():
262262
t = pd.date_range(start="2000-01-01", end="2000-01-28", freq="1D")
263263
values = 1 + np.arange(t.size)
264264
precip = xr.DataArray(values, coords={"T": t})
265-
precip_int = calc.regroup(precip, group=4, method="sum")
265+
precip_int = calc.regroup(precip, group=4).sum()
266266

267267
np.testing.assert_array_equal(
268268
precip_int,
@@ -274,7 +274,7 @@ def test_resample_interval_to_daily():
274274
t = pd.date_range(start="2000-01-01", end="2000-01-28", freq="1D")
275275
values = 1 + np.arange(t.size)
276276
precip = xr.DataArray(values, coords={"T": t})
277-
precip_pentad = calc.regroup(precip, group="pentad", method="sum")
277+
precip_pentad = calc.regroup(precip, group="pentad").sum()
278278
precip_daily = calc.resample_interval_to_daily(precip_pentad)
279279

280280
np.testing.assert_array_equal(precip_daily, [
@@ -287,7 +287,7 @@ def test_resample_interval_to_daily_intensive():
287287
t = pd.date_range(start="2000-01-01", end="2000-01-28", freq="1D")
288288
values = 1 + np.arange(t.size)
289289
precip = xr.DataArray(values, coords={"T": t}, attrs={"units": "mm/day"})
290-
precip_pentad = calc.regroup(precip, group="pentad", method="mean")
290+
precip_pentad = calc.regroup(precip, group="pentad").mean()
291291
precip_daily = calc.resample_interval_to_daily(precip_pentad)
292292

293293
np.testing.assert_array_equal(precip_daily, [
@@ -630,6 +630,37 @@ def test_seasonal_onset_date_keeps_returning_same_outputs():
630630
),
631631
)
632632

633+
def test_seasonal_onset_date_keeps_returning_same_outputs_with_regroup():
634+
precip = data_test_calc.multi_year_data_sample()
635+
onsetsds = calc.regroup(
636+
time_series=precip, group="1 Mar - 20 Jun"
637+
).map(calc.onset_date, **{
638+
"wet_thresh": 1,
639+
"wet_spell_length": 3,
640+
"wet_spell_thresh": 20,
641+
"min_wet_days": 1,
642+
"dry_spell_length": 7,
643+
"dry_spell_search": 21,
644+
})
645+
# That part could be included in regroup for this specific group case
646+
onsetsds = onsetsds.isel(T_bins=np.arange(0, onsetsds.size, 2), drop=True)
647+
# Note that onset_date is written and such a manner that is also outputs T, while
648+
# regroup brings intervals T_bins. T_bins is enough so onset_date could possibly
649+
# be rewritten accordingly
650+
onsets = (onsetsds + onsetsds["T"])
651+
652+
np.testing.assert_array_equal(
653+
onsets,
654+
pd.to_datetime(
655+
[
656+
"NaT",
657+
"2001-03-08T00:00:00.000000000",
658+
"NaT",
659+
"2003-04-12T00:00:00.000000000",
660+
"2004-04-04T00:00:00.000000000",
661+
],
662+
),
663+
)
633664

634665
def test_seasonal_cess_date_keeps_returning_same_outputs():
635666

@@ -663,6 +694,38 @@ def test_seasonal_cess_date_keeps_returning_same_outputs():
663694
),
664695
)
665696

697+
def test_seasonal_cess_date_keeps_returning_same_outputs_with_regroup():
698+
699+
precip = data_test_calc.multi_year_data_sample()
700+
wb = calc.water_balance(
701+
daily_rain=precip,
702+
et=5,
703+
taw=60,
704+
sminit=0,
705+
time_dim="T"
706+
).to_array(name="soil moisture").squeeze("variable", drop=True)
707+
cessds = calc.regroup(
708+
time_series=wb, group="1 Sep - 30 Nov"
709+
).map(calc.cess_date_from_sm, **{
710+
"dry_thresh": 5,
711+
"dry_spell_length_thresh": 3,
712+
})
713+
# Not sure what happened to T_bins here
714+
cessds = cessds.isel(T=np.arange(0, cessds.size, 2), drop=True)
715+
cess = (cessds + cessds["T"]).squeeze()
716+
np.testing.assert_array_equal(
717+
cess,
718+
pd.to_datetime(
719+
[
720+
"2000-09-21T00:00:00.000000000",
721+
"2001-09-03T00:00:00.000000000",
722+
"2002-09-03T00:00:00.000000000",
723+
"2003-09-24T00:00:00.000000000",
724+
"2004-09-01T00:00:00.000000000",
725+
],
726+
),
727+
)
728+
666729

667730
def test_seasonal_cess_date_from_rain_keeps_returning_same_outputs():
668731

@@ -683,6 +746,24 @@ def test_seasonal_cess_date_from_rain_keeps_returning_same_outputs():
683746
assert cess[0] == pd.to_datetime("2000-09-21T00:00:00.000000000")
684747

685748

749+
def test_seasonal_cess_date_from_rain_keeps_returning_same_outputs_with_regroup():
750+
751+
precip = data_test_calc.multi_year_data_sample()
752+
cessds = calc.regroup(
753+
time_series=precip, group="1 Sep - 30 Nov"
754+
).map(calc.cess_date_from_rain, **{
755+
"dry_thresh": 5,
756+
"dry_spell_length_thresh": 3,
757+
"et": 5,
758+
"taw": 60,
759+
"sminit": 33.57026932, # from previous test sm output on 8/31/2000
760+
})
761+
cessds = cessds.isel(T=np.arange(0, cessds.size, 2), drop=True)
762+
cess = (cessds + cessds["T"]).squeeze()
763+
764+
assert cess[0] == pd.to_datetime("2000-09-21T00:00:00.000000000")
765+
766+
686767
def test_seasonal_onset_date():
687768
t = pd.date_range(start="2000-01-01", end="2005-02-28", freq="1D")
688769
# this is rr_mrg.sel(T=slice("2000", "2005-02-28")).isel(X=150, Y=150).precip
@@ -764,19 +845,15 @@ def test_seasonal_onset_date_with_regroup():
764845
).rename("synthetic_precip")
765846

766847
onsetsds = calc.regroup(
767-
time_series=synthetic_precip,
768-
group="1 Mar - 20 Jun",
769-
method="map",
770-
method_kwargs={
771-
"func": calc.onset_date,
848+
time_series=synthetic_precip, group="1 Mar - 20 Jun"
849+
).map(calc.onset_date, **{
772850
"wet_thresh": 1,
773851
"wet_spell_length": 3,
774852
"wet_spell_thresh": 20,
775853
"min_wet_days": 1,
776854
"dry_spell_length": 7,
777855
"dry_spell_search": 21,
778-
},
779-
)
856+
})
780857
onsetsds = onsetsds.isel(T_bins=np.arange(0, onsetsds.size, 2), drop=True)
781858
onsets = (onsetsds + onsetsds["T"]).drop_vars("T")
782859

@@ -885,15 +962,11 @@ def test_seasonal_cess_date_with_regroup():
885962
time_dim="T"
886963
).to_array(name="soil moisture")
887964
cessds = calc.regroup(
888-
time_series=wb,
889-
group="1 Sep - 30 Nov",
890-
method="map",
891-
method_kwargs={
892-
"func": calc.cess_date_from_sm,
965+
time_series=wb, group="1 Sep - 30 Nov",
966+
).map(calc.cess_date_from_sm, **{
893967
"dry_thresh": 5,
894968
"dry_spell_length_thresh": 3,
895-
},
896-
)
969+
})
897970
cessds = cessds.isel(T=np.arange(0, cessds.size, 2), drop=True)
898971
cess = (cessds + cessds["T"]).squeeze(drop=True)
899972

@@ -987,18 +1060,14 @@ def test_seasonal_cess_date_from_rain_with_regroup():
9871060
synthetic_precip,
9881061
).rename("synthetic_precip")
9891062
cessds = calc.regroup(
990-
time_series=synthetic_precip,
991-
group="1 Sep - 30 Nov",
992-
method="map",
993-
method_kwargs={
994-
"func": calc.cess_date_from_rain,
1063+
time_series=synthetic_precip, group="1 Sep - 30 Nov"
1064+
).map(calc.cess_date_from_rain, **{
9951065
"dry_thresh": 5,
9961066
"dry_spell_length_thresh": 3,
9971067
"et": 5,
9981068
"taw": 60,
9991069
"sminit": 0,
1000-
},
1001-
)
1070+
})
10021071
cessds = cessds.isel(T=np.arange(0, cessds.size, 2), drop=True)
10031072
cess = (cessds + cessds["T"]).squeeze()
10041073

0 commit comments

Comments
 (0)