@@ -12,12 +12,19 @@ class Weekday:
12
12
"""Class to handle weekday effects."""
13
13
14
14
@staticmethod
15
- def get_params (data , denominator_col , numerator_cols , date_col , scales , logger ):
15
+ def get_params (data , denominator_col , numerator_cols , date_col , scales , logger , solver_override = None ):
16
16
r"""Fit weekday correction for each col in numerator_cols.
17
17
18
18
Return a matrix of parameters: the entire vector of betas, for each time
19
19
series column in the data.
20
+
21
+ solver: Historically used "ECOS" but due to numerical stability issues, "CLARABEL"
22
+ (introduced in cvxpy 1.3)is now the default solver in cvxpy 1.5.
20
23
"""
24
+ if solver_override is None :
25
+ solver = cp .CLARABEL
26
+ else :
27
+ solver = solver_override
21
28
tmp = data .reset_index ()
22
29
denoms = tmp .groupby (date_col ).sum ()[denominator_col ]
23
30
nums = tmp .groupby (date_col ).sum ()[numerator_cols ]
@@ -35,7 +42,7 @@ def get_params(data, denominator_col, numerator_cols, date_col, scales, logger):
35
42
36
43
# Loop over the available numerator columns and smooth each separately.
37
44
for i in range (nums .shape [1 ]):
38
- result = Weekday ._fit (X , scales , npnums [:, i ], npdenoms )
45
+ result = Weekday ._fit (X , scales , npnums [:, i ], npdenoms , solver )
39
46
if result is None :
40
47
logger .error ("Unable to calculate weekday correction" )
41
48
else :
@@ -44,7 +51,18 @@ def get_params(data, denominator_col, numerator_cols, date_col, scales, logger):
44
51
return params
45
52
46
53
@staticmethod
47
- def _fit (X , scales , npnums , npdenoms ):
54
+ def get_params_legacy (data , denominator_col , numerator_cols , date_col , scales , logger ):
55
+ r"""
56
+ Preserves older default behavior of using the ECOS solver.
57
+
58
+ NOTE: "ECOS" solver will not be installed by default as of cvxpy 1.6
59
+ """
60
+ return Weekday .get_params (
61
+ data , denominator_col , numerator_cols , date_col , scales , logger , solver_override = cp .ECOS
62
+ )
63
+
64
+ @staticmethod
65
+ def _fit (X , scales , npnums , npdenoms , solver ):
48
66
r"""Correct a signal estimated as numerator/denominator for weekday effects.
49
67
50
68
The ordinary estimate would be numerator_t/denominator_t for each time point
@@ -78,6 +96,8 @@ def _fit(X, scales, npnums, npdenoms):
78
96
79
97
ll = (numerator * (X*b + log(denominator)) - sum(exp(X*b) + log(denominator)))
80
98
/ num_days
99
+
100
+ solver: Historically use "ECOS" but due to numerical issues, "CLARABEL" is now default.
81
101
"""
82
102
b = cp .Variable ((X .shape [1 ]))
83
103
@@ -93,7 +113,7 @@ def _fit(X, scales, npnums, npdenoms):
93
113
for scale in scales :
94
114
try :
95
115
prob = cp .Problem (cp .Minimize ((- ll + lmbda * penalty ) / scale ))
96
- _ = prob .solve (solver = cp . CLARABEL )
116
+ _ = prob .solve (solver = solver )
97
117
return b .value
98
118
except SolverError :
99
119
# If the magnitude of the objective function is too large, an error is
0 commit comments