Skip to content

Commit 9c08fe1

Browse files
CLN: Splits Moments and MomentsConsistency tests into separate files (#34140)
1 parent 6c0be4b commit 9c08fe1

5 files changed

+988
-970
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,284 @@
1+
import numpy as np
2+
from numpy.random import randn
3+
import pytest
4+
5+
from pandas import DataFrame, Series, concat
6+
from pandas.tests.window.common import (
7+
Base,
8+
check_binary_ew,
9+
check_binary_ew_min_periods,
10+
check_pairwise_moment,
11+
ew_func,
12+
moments_consistency_cov_data,
13+
moments_consistency_is_constant,
14+
moments_consistency_mock_mean,
15+
moments_consistency_series_data,
16+
moments_consistency_std_data,
17+
moments_consistency_var_data,
18+
moments_consistency_var_debiasing_factors,
19+
)
20+
21+
22+
class TestEwmMomentsConsistency(Base):
23+
def setup_method(self, method):
24+
self._create_data()
25+
26+
@pytest.mark.parametrize("func", ["cov", "corr"])
27+
def test_ewm_pairwise_cov_corr(self, func):
28+
check_pairwise_moment(self.frame, "ewm", func, span=10, min_periods=5)
29+
30+
31+
@pytest.mark.parametrize("name", ["cov", "corr"])
32+
def test_ewm_corr_cov(name, min_periods, binary_ew_data):
33+
A, B = binary_ew_data
34+
35+
check_binary_ew(name="corr", A=A, B=B)
36+
check_binary_ew_min_periods("corr", min_periods, A, B)
37+
38+
39+
@pytest.mark.parametrize("name", ["cov", "corr"])
40+
def test_different_input_array_raise_exception(name, binary_ew_data):
41+
42+
A, _ = binary_ew_data
43+
msg = "Input arrays must be of the same type!"
44+
# exception raised is Exception
45+
with pytest.raises(Exception, match=msg):
46+
ew_func(A, randn(50), 20, name=name, min_periods=5)
47+
48+
49+
@pytest.mark.slow
50+
@pytest.mark.parametrize("min_periods", [0, 1, 2, 3, 4])
51+
@pytest.mark.parametrize("adjust", [True, False])
52+
@pytest.mark.parametrize("ignore_na", [True, False])
53+
def test_ewm_consistency(consistency_data, min_periods, adjust, ignore_na):
54+
def _weights(s, com, adjust, ignore_na):
55+
if isinstance(s, DataFrame):
56+
if not len(s.columns):
57+
return DataFrame(index=s.index, columns=s.columns)
58+
w = concat(
59+
[
60+
_weights(s.iloc[:, i], com=com, adjust=adjust, ignore_na=ignore_na)
61+
for i, _ in enumerate(s.columns)
62+
],
63+
axis=1,
64+
)
65+
w.index = s.index
66+
w.columns = s.columns
67+
return w
68+
69+
w = Series(np.nan, index=s.index)
70+
alpha = 1.0 / (1.0 + com)
71+
if ignore_na:
72+
w[s.notna()] = _weights(
73+
s[s.notna()], com=com, adjust=adjust, ignore_na=False
74+
)
75+
elif adjust:
76+
for i in range(len(s)):
77+
if s.iat[i] == s.iat[i]:
78+
w.iat[i] = pow(1.0 / (1.0 - alpha), i)
79+
else:
80+
sum_wts = 0.0
81+
prev_i = -1
82+
for i in range(len(s)):
83+
if s.iat[i] == s.iat[i]:
84+
if prev_i == -1:
85+
w.iat[i] = 1.0
86+
else:
87+
w.iat[i] = alpha * sum_wts / pow(1.0 - alpha, i - prev_i)
88+
sum_wts += w.iat[i]
89+
prev_i = i
90+
return w
91+
92+
def _variance_debiasing_factors(s, com, adjust, ignore_na):
93+
weights = _weights(s, com=com, adjust=adjust, ignore_na=ignore_na)
94+
cum_sum = weights.cumsum().fillna(method="ffill")
95+
cum_sum_sq = (weights * weights).cumsum().fillna(method="ffill")
96+
numerator = cum_sum * cum_sum
97+
denominator = numerator - cum_sum_sq
98+
denominator[denominator <= 0.0] = np.nan
99+
return numerator / denominator
100+
101+
def _ewma(s, com, min_periods, adjust, ignore_na):
102+
weights = _weights(s, com=com, adjust=adjust, ignore_na=ignore_na)
103+
result = (
104+
s.multiply(weights).cumsum().divide(weights.cumsum()).fillna(method="ffill")
105+
)
106+
result[
107+
s.expanding().count() < (max(min_periods, 1) if min_periods else 1)
108+
] = np.nan
109+
return result
110+
111+
x, is_constant, no_nans = consistency_data
112+
com = 3.0
113+
moments_consistency_mock_mean(
114+
x=x,
115+
mean=lambda x: x.ewm(
116+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
117+
).mean(),
118+
mock_mean=lambda x: _ewma(
119+
x, com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
120+
),
121+
)
122+
123+
moments_consistency_is_constant(
124+
x=x,
125+
is_constant=is_constant,
126+
min_periods=min_periods,
127+
count=lambda x: x.expanding().count(),
128+
mean=lambda x: x.ewm(
129+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
130+
).mean(),
131+
corr=lambda x, y: x.ewm(
132+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
133+
).corr(y),
134+
)
135+
136+
moments_consistency_var_debiasing_factors(
137+
x=x,
138+
var_unbiased=lambda x: (
139+
x.ewm(
140+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
141+
).var(bias=False)
142+
),
143+
var_biased=lambda x: (
144+
x.ewm(
145+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
146+
).var(bias=True)
147+
),
148+
var_debiasing_factors=lambda x: (
149+
_variance_debiasing_factors(x, com=com, adjust=adjust, ignore_na=ignore_na)
150+
),
151+
)
152+
153+
154+
@pytest.mark.parametrize("min_periods", [0, 1, 2, 3, 4])
155+
@pytest.mark.parametrize("adjust", [True, False])
156+
@pytest.mark.parametrize("ignore_na", [True, False])
157+
def test_ewm_consistency_var(consistency_data, min_periods, adjust, ignore_na):
158+
x, is_constant, no_nans = consistency_data
159+
com = 3.0
160+
moments_consistency_var_data(
161+
x=x,
162+
is_constant=is_constant,
163+
min_periods=min_periods,
164+
count=lambda x: x.expanding().count(),
165+
mean=lambda x: x.ewm(
166+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
167+
).mean(),
168+
var_unbiased=lambda x: (
169+
x.ewm(
170+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
171+
).var(bias=False)
172+
),
173+
var_biased=lambda x: (
174+
x.ewm(
175+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
176+
).var(bias=True)
177+
),
178+
)
179+
180+
181+
@pytest.mark.parametrize("min_periods", [0, 1, 2, 3, 4])
182+
@pytest.mark.parametrize("adjust", [True, False])
183+
@pytest.mark.parametrize("ignore_na", [True, False])
184+
def test_ewm_consistency_std(consistency_data, min_periods, adjust, ignore_na):
185+
x, is_constant, no_nans = consistency_data
186+
com = 3.0
187+
moments_consistency_std_data(
188+
x=x,
189+
var_unbiased=lambda x: (
190+
x.ewm(
191+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
192+
).var(bias=False)
193+
),
194+
std_unbiased=lambda x: (
195+
x.ewm(
196+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
197+
).std(bias=False)
198+
),
199+
var_biased=lambda x: (
200+
x.ewm(
201+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
202+
).var(bias=True)
203+
),
204+
std_biased=lambda x: x.ewm(
205+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
206+
).std(bias=True),
207+
)
208+
209+
210+
@pytest.mark.parametrize("min_periods", [0, 1, 2, 3, 4])
211+
@pytest.mark.parametrize("adjust", [True, False])
212+
@pytest.mark.parametrize("ignore_na", [True, False])
213+
def test_ewm_consistency_cov(consistency_data, min_periods, adjust, ignore_na):
214+
x, is_constant, no_nans = consistency_data
215+
com = 3.0
216+
moments_consistency_cov_data(
217+
x=x,
218+
var_unbiased=lambda x: (
219+
x.ewm(
220+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
221+
).var(bias=False)
222+
),
223+
cov_unbiased=lambda x, y: (
224+
x.ewm(
225+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
226+
).cov(y, bias=False)
227+
),
228+
var_biased=lambda x: (
229+
x.ewm(
230+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
231+
).var(bias=True)
232+
),
233+
cov_biased=lambda x, y: (
234+
x.ewm(
235+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
236+
).cov(y, bias=True)
237+
),
238+
)
239+
240+
241+
@pytest.mark.slow
242+
@pytest.mark.parametrize("min_periods", [0, 1, 2, 3, 4])
243+
@pytest.mark.parametrize("adjust", [True, False])
244+
@pytest.mark.parametrize("ignore_na", [True, False])
245+
def test_ewm_consistency_series_data(consistency_data, min_periods, adjust, ignore_na):
246+
x, is_constant, no_nans = consistency_data
247+
com = 3.0
248+
moments_consistency_series_data(
249+
x=x,
250+
mean=lambda x: x.ewm(
251+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
252+
).mean(),
253+
corr=lambda x, y: x.ewm(
254+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
255+
).corr(y),
256+
var_unbiased=lambda x: (
257+
x.ewm(
258+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
259+
).var(bias=False)
260+
),
261+
std_unbiased=lambda x: (
262+
x.ewm(
263+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
264+
).std(bias=False)
265+
),
266+
cov_unbiased=lambda x, y: (
267+
x.ewm(
268+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
269+
).cov(y, bias=False)
270+
),
271+
var_biased=lambda x: (
272+
x.ewm(
273+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
274+
).var(bias=True)
275+
),
276+
std_biased=lambda x: x.ewm(
277+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
278+
).std(bias=True),
279+
cov_biased=lambda x, y: (
280+
x.ewm(
281+
com=com, min_periods=min_periods, adjust=adjust, ignore_na=ignore_na
282+
).cov(y, bias=True)
283+
),
284+
)

0 commit comments

Comments
 (0)