11
11
from ..utils .seq_dataset import ArrayDataset , CSRDataset
12
12
from ..externals import six
13
13
from ..externals .joblib import Parallel , delayed
14
- from .sag_fast import Log , SquaredLoss
14
+ from .sag_fast import LogLoss , SquaredLoss
15
15
from .sag_fast import sag_sparse , get_auto_eta
16
16
17
17
MAX_INT = np .iinfo (np .int32 ).max
21
21
SPARSE_INTERCEPT_DECAY = 0.01
22
22
23
23
24
+ def make_dataset (X , y , sample_weight , random_state ):
25
+ # check which type of Sequential Dataset is needed
26
+ if sp .issparse (X ):
27
+ dataset = CSRDataset (X .data , X .indptr , X .indices ,
28
+ y , sample_weight ,
29
+ seed = random_state .randint (MAX_INT ))
30
+ intercept_decay = SPARSE_INTERCEPT_DECAY
31
+ else :
32
+ dataset = ArrayDataset (X , y , sample_weight ,
33
+ seed = random_state .randint (MAX_INT ))
34
+ intercept_decay = 1.0
35
+
36
+ return dataset , intercept_decay
37
+
38
+
39
+ def sag_ridge (X , y , alpha = 1e-4 , sample_weight = None , max_iter = 1000 , tol = 0.001 ,
40
+ verbose = 0 ):
41
+ """SAG solver for Ridge regression"""
42
+
43
+ # TODO
44
+ if max_iter is None :
45
+ warnings .warn ("sag solver requires 'max_iter' to be not None. "
46
+ "max_iter is set to 1000" , RuntimeWarning )
47
+ max_iter = 1000
48
+
49
+ n_samples , n_features = X .shape [0 ], X .shape [1 ]
50
+ alpha = float (alpha ) / n_samples
51
+ fit_intercept = False
52
+
53
+ # initialization
54
+ if sample_weight is None :
55
+ sample_weight = np .ones (n_samples , dtype = np .float64 , order = 'C' )
56
+ coef_init = np .zeros (n_features , dtype = np .float64 , order = 'C' )
57
+ intercept_init = 0.0
58
+ weight_pos = 1
59
+ weight_neg = 1
60
+
61
+ # TODO: *_init (with a boolean warm-start) as parameters ?
62
+ intercept_sum_gradient_init = 0.0
63
+ sum_gradient_init = np .zeros (n_features , dtype = np .float64 , order = 'C' )
64
+ gradient_memory_init = np .zeros (n_samples , dtype = np .float64 , order = 'C' )
65
+ seen_init = np .zeros (n_samples , dtype = np .int32 , order = 'C' )
66
+ num_seen_init = 0
67
+
68
+ # TODO: add a random_state in parameters ?
69
+ random_state = check_random_state (42 )
70
+
71
+ dataset , intercept_decay = make_dataset (X , y , sample_weight , random_state )
72
+
73
+ # set the eta0 at 1 / 4L where L is the max sum of
74
+ # squares for over all samples
75
+ step_size = get_auto_eta (dataset , alpha , n_samples , SquaredLoss (),
76
+ fit_intercept )
77
+ if step_size * alpha == 1 :
78
+ raise ZeroDivisionError ("Current sag implementation does not handle "
79
+ "the case step_size * alpha == 1" )
80
+ print alpha
81
+ intercept_ , num_seen , max_iter_reached , intercept_sum_gradient = \
82
+ sag_sparse (dataset , coef_init .ravel (),
83
+ intercept_init , n_samples ,
84
+ n_features , tol ,
85
+ max_iter ,
86
+ SquaredLoss (),
87
+ step_size , alpha ,
88
+ sum_gradient_init .ravel (),
89
+ gradient_memory_init .ravel (),
90
+ seen_init .ravel (),
91
+ num_seen_init ,
92
+ weight_pos , weight_neg ,
93
+ fit_intercept ,
94
+ intercept_sum_gradient_init ,
95
+ intercept_decay ,
96
+ verbose )
97
+
98
+ if max_iter_reached :
99
+ warnings .warn ("The max_iter was reached which means "
100
+ "the coef_ did not converge" , ConvergenceWarning )
101
+
102
+ return coef_init
103
+
104
+
24
105
def sag_logistic (X , y , coef_init , alpha = 1e-4 , sample_weight = None ,
25
106
max_iter = 1000 , tol = 0.001 , verbose = 0 , random_state = None ):
26
107
"""SAG solver for LogisticRegression"""
27
108
28
109
n_samples , n_features = X .shape [0 ], X .shape [1 ]
110
+ alpha = float (alpha ) / n_samples
29
111
30
- alpha = alpha / n_samples
31
-
32
- # initialize all parameters if there is no init
33
112
if sample_weight is None :
34
113
sample_weight = np .ones (n_samples , dtype = np .float64 , order = 'C' )
35
114
@@ -47,32 +126,28 @@ def sag_logistic(X, y, coef_init, alpha=1e-4, sample_weight=None,
47
126
gradient_memory_init = np .zeros (n_samples , dtype = np .float64 , order = 'C' )
48
127
seen_init = np .zeros (n_samples , dtype = np .int32 , order = 'C' )
49
128
num_seen_init = 0
129
+
50
130
weight_pos = 1
51
131
weight_neg = 1
52
132
53
133
random_state = check_random_state (random_state )
54
134
55
- # check which type of Sequential Dataset is needed
56
- if sp .issparse (X ):
57
- dataset = CSRDataset (X .data , X .indptr , X .indices ,
58
- y , sample_weight ,
59
- seed = random_state .randint (MAX_INT ))
60
- intercept_decay = SPARSE_INTERCEPT_DECAY
61
- else :
62
- dataset = ArrayDataset (X , y , sample_weight ,
63
- seed = random_state .randint (MAX_INT ))
64
- intercept_decay = 1.0
135
+ dataset , intercept_decay = make_dataset (X , y , sample_weight , random_state )
65
136
66
137
# set the eta0 at 1 / 4L where L is the max sum of
67
138
# squares for over all samples
68
- step_size = get_auto_eta (dataset , alpha , n_samples , Log (), fit_intercept )
139
+ step_size = get_auto_eta (dataset , alpha , n_samples , LogLoss (),
140
+ fit_intercept )
141
+ if step_size * alpha == 1. :
142
+ raise ZeroDivisionError ("Current sag implementation does not handle "
143
+ "the case step_size * alpha == 1" )
69
144
70
145
intercept_ , num_seen , max_iter_reached , intercept_sum_gradient = \
71
146
sag_sparse (dataset , coef_init .ravel (),
72
147
intercept_init , n_samples
10712
,
73
148
n_features , tol ,
74
149
max_iter ,
75
- Log (),
150
+ LogLoss (),
76
151
step_size , alpha ,
77
152
sum_gradient_init .ravel (),
78
153
gradient_memory_init .ravel (),
@@ -163,16 +238,8 @@ def _fit(self, X, y, coef_init=None, intercept_init=None,
163
238
164
239
random_state = check_random_state (self .random_state )
165
240
166
- # check which type of Sequential Dataset is needed
167
- if sp .issparse (X ):
168
- dataset = CSRDataset (X .data , X .indptr , X .indices ,
169
- y , sample_weight ,
170
- seed = random_state .randint (MAX_INT ))
171
- intercept_decay = SPARSE_INTERCEPT_DECAY
172
- else :
173
- dataset = ArrayDataset (X , y , sample_weight ,
174
- seed = random_state .randint (MAX_INT ))
175
- intercept_decay = 1.0
241
+ dataset , intercept_decay = make_dataset (X , y , sample_weight ,
242
+ random_state )
176
243
177
244
# set the eta0 if needed, 'auto' is 1 / 4L where L is the max sum of
178
245
# squares for over all samples
@@ -317,7 +384,7 @@ def __init__(self, alpha=0.0001,
317
384
eta0 = 'auto' , class_weight = None , warm_start = False ):
318
385
self .n_jobs = n_jobs
319
386
self .class_weight = class_weight
320
- self .loss_function = Log ()
387
+ self .loss_function = LogLoss ()
321
388
super (SAGClassifier , self ).__init__ (alpha = alpha ,
322
389
fit_intercept = fit_intercept ,
323
390
max_iter = max_iter ,
0 commit comments