scikit-base 0.4.6__py3-none-any.whl → 0.5.1__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- docs/source/conf.py +299 -299
- {scikit_base-0.4.6.dist-info → scikit_base-0.5.1.dist-info}/LICENSE +29 -29
- {scikit_base-0.4.6.dist-info → scikit_base-0.5.1.dist-info}/METADATA +160 -159
- scikit_base-0.5.1.dist-info/RECORD +58 -0
- {scikit_base-0.4.6.dist-info → scikit_base-0.5.1.dist-info}/WHEEL +1 -1
- scikit_base-0.5.1.dist-info/top_level.txt +5 -0
- {scikit_base-0.4.6.dist-info → scikit_base-0.5.1.dist-info}/zip-safe +1 -1
- skbase/__init__.py +14 -14
- skbase/_exceptions.py +31 -31
- skbase/_nopytest_tests.py +35 -35
- skbase/base/__init__.py +20 -20
- skbase/base/_base.py +1249 -1249
- skbase/base/_meta.py +883 -871
- skbase/base/_pretty_printing/__init__.py +11 -11
- skbase/base/_pretty_printing/_object_html_repr.py +392 -392
- skbase/base/_pretty_printing/_pprint.py +412 -412
- skbase/base/_tagmanager.py +217 -217
- skbase/lookup/__init__.py +31 -31
- skbase/lookup/_lookup.py +1009 -1009
- skbase/lookup/tests/__init__.py +2 -2
- skbase/lookup/tests/test_lookup.py +991 -991
- skbase/testing/__init__.py +12 -12
- skbase/testing/test_all_objects.py +852 -856
- skbase/testing/utils/__init__.py +5 -5
- skbase/testing/utils/_conditional_fixtures.py +209 -209
- skbase/testing/utils/_dependencies.py +15 -15
- skbase/testing/utils/deep_equals.py +15 -15
- skbase/testing/utils/inspect.py +30 -30
- skbase/testing/utils/tests/__init__.py +2 -2
- skbase/testing/utils/tests/test_check_dependencies.py +49 -49
- skbase/testing/utils/tests/test_deep_equals.py +66 -66
- skbase/tests/__init__.py +2 -2
- skbase/tests/conftest.py +273 -273
- skbase/tests/mock_package/__init__.py +5 -5
- skbase/tests/mock_package/test_mock_package.py +74 -74
- skbase/tests/test_base.py +1202 -1202
- skbase/tests/test_baseestimator.py +130 -130
- skbase/tests/test_exceptions.py +23 -23
- skbase/tests/test_meta.py +170 -131
- skbase/utils/__init__.py +21 -21
- skbase/utils/_check.py +53 -53
- skbase/utils/_iter.py +238 -238
- skbase/utils/_nested_iter.py +180 -180
- skbase/utils/_utils.py +91 -91
- skbase/utils/deep_equals.py +358 -358
- skbase/utils/dependencies/__init__.py +11 -11
- skbase/utils/dependencies/_dependencies.py +253 -253
- skbase/utils/tests/__init__.py +4 -4
- skbase/utils/tests/test_check.py +24 -24
- skbase/utils/tests/test_iter.py +127 -127
- skbase/utils/tests/test_nested_iter.py +84 -84
- skbase/utils/tests/test_utils.py +37 -37
- skbase/validate/__init__.py +22 -22
- skbase/validate/_named_objects.py +403 -403
- skbase/validate/_types.py +345 -345
- skbase/validate/tests/__init__.py +2 -2
- skbase/validate/tests/test_iterable_named_objects.py +200 -200
- skbase/validate/tests/test_type_validations.py +370 -370
- scikit_base-0.4.6.dist-info/RECORD +0 -58
- scikit_base-0.4.6.dist-info/top_level.txt +0 -2
@@ -1,392 +1,392 @@
|
|
1
|
-
# -*- coding: utf-8 -*-
|
2
|
-
# copyright: skbase developers, BSD-3-Clause License (see LICENSE file)
|
3
|
-
# Many elements of this code were developed in scikit-learn. These elements
|
4
|
-
# are copyrighted by the scikit-learn developers, BSD-3-Clause License. For
|
5
|
-
# conditions see https://github.com/scikit-learn/scikit-learn/blob/main/COPYING
|
6
|
-
"""Functionality to represent instance of BaseObject as html."""
|
7
|
-
|
8
|
-
import html
|
9
|
-
import uuid
|
10
|
-
from contextlib import closing
|
11
|
-
from io import StringIO
|
12
|
-
from string import Template
|
13
|
-
|
14
|
-
__author__ = ["RNKuhns"]
|
15
|
-
|
16
|
-
|
17
|
-
class _VisualBlock:
|
18
|
-
"""HTML Representation of BaseObject.
|
19
|
-
|
20
|
-
Parameters
|
21
|
-
----------
|
22
|
-
kind : {'serial', 'parallel', 'single'}
|
23
|
-
kind of HTML block
|
24
|
-
|
25
|
-
objs : list of BaseObjects or `_VisualBlock`s or a single BaseObject
|
26
|
-
If kind != 'single', then `objs` is a list of
|
27
|
-
BaseObjects. If kind == 'single', then `objs` is a single BaseObject.
|
28
|
-
|
29
|
-
names : list of str, default=None
|
30
|
-
If kind != 'single', then `names` corresponds to BaseObjects.
|
31
|
-
If kind == 'single', then `names` is a single string corresponding to
|
32
|
-
the single BaseObject.
|
33
|
-
|
34
|
-
name_details : list of str, str, or None, default=None
|
35
|
-
If kind != 'single', then `name_details` corresponds to `names`.
|
36
|
-
If kind == 'single', then `name_details` is a single string
|
37
|
-
corresponding to the single BaseObject.
|
38
|
-
|
39
|
-
dash_wrapped : bool, default=True
|
40
|
-
If true, wrapped HTML element will be wrapped with a dashed border.
|
41
|
-
Only active when kind != 'single'.
|
42
|
-
"""
|
43
|
-
|
44
|
-
def __init__(self, kind, objs, *, names=None, name_details=None, dash_wrapped=True):
|
45
|
-
self.kind = kind
|
46
|
-
self.objs = objs
|
47
|
-
self.dash_wrapped = dash_wrapped
|
48
|
-
|
49
|
-
if self.kind in ("parallel", "serial"):
|
50
|
-
if names is None:
|
51
|
-
names = (None,) * len(objs)
|
52
|
-
if name_details is None:
|
53
|
-
name_details = (None,) * len(objs)
|
54
|
-
|
55
|
-
self.names = names
|
56
|
-
self.name_details = name_details
|
57
|
-
|
58
|
-
def _sk_visual_block_(self):
|
59
|
-
return self
|
60
|
-
|
61
|
-
|
62
|
-
def _write_label_html(
|
63
|
-
out,
|
64
|
-
name,
|
65
|
-
name_details,
|
66
|
-
outer_class="sk-label-container",
|
67
|
-
inner_class="sk-label",
|
68
|
-
checked=False,
|
69
|
-
):
|
70
|
-
"""Write labeled html with or without a dropdown with named details."""
|
71
|
-
out.write(f'<div class={outer_class!r}><div class="{inner_class} sk-toggleable">')
|
72
|
-
name = html.escape(name)
|
73
|
-
|
74
|
-
if name_details is not None:
|
75
|
-
name_details = html.escape(str(name_details))
|
76
|
-
label_class = "sk-toggleable__label sk-toggleable__label-arrow"
|
77
|
-
|
78
|
-
checked_str = "checked" if checked else ""
|
79
|
-
est_id = uuid.uuid4()
|
80
|
-
out.write(
|
81
|
-
'<input class="sk-toggleable__control sk-hidden--visually" '
|
82
|
-
f'id={est_id!r} type="checkbox" {checked_str}>'
|
83
|
-
f"<label for={est_id!r} class={label_class!r}>{name}</label>"
|
84
|
-
f'<div class="sk-toggleable__content"><pre>{name_details}'
|
85
|
-
"</pre></div>"
|
86
|
-
)
|
87
|
-
else:
|
88
|
-
out.write(f"<label>{name}</label>")
|
89
|
-
out.write("</div></div>") # outer_class inner_class
|
90
|
-
|
91
|
-
|
92
|
-
def _get_visual_block(base_object):
|
93
|
-
"""Generate information about how to display a BaseObject."""
|
94
|
-
if hasattr(base_object, "_sk_visual_block_"):
|
95
|
-
return base_object._sk_visual_block_()
|
96
|
-
|
97
|
-
if isinstance(base_object, str):
|
98
|
-
return _VisualBlock(
|
99
|
-
"single", base_object, names=base_object, name_details=base_object
|
100
|
-
)
|
101
|
-
elif base_object is None:
|
102
|
-
return _VisualBlock("single", base_object, names="None", name_details="None")
|
103
|
-
|
104
|
-
# check if base_object looks like a meta base_object wraps base_object
|
105
|
-
if hasattr(base_object, "get_params"):
|
106
|
-
base_objects = []
|
107
|
-
for key, value in base_object.get_params().items():
|
108
|
-
# Only look at the BaseObjects in the first layer
|
109
|
-
if "__" not in key and hasattr(value, "get_params"):
|
110
|
-
base_objects.append(value)
|
111
|
-
if len(base_objects):
|
112
|
-
return _VisualBlock("parallel", base_objects, names=None)
|
113
|
-
|
114
|
-
return _VisualBlock(
|
115
|
-
"single",
|
116
|
-
base_object,
|
117
|
-
names=base_object.__class__.__name__,
|
118
|
-
name_details=str(base_object),
|
119
|
-
)
|
120
|
-
|
121
|
-
|
122
|
-
def _write_base_object_html(
|
123
|
-
out, base_object, base_object_label, base_object_label_details, first_call=False
|
124
|
-
):
|
125
|
-
"""Write BaseObject to html in serial, parallel, or by itself (single)."""
|
126
|
-
est_block = _get_visual_block(base_object)
|
127
|
-
|
128
|
-
if est_block.kind in ("serial", "parallel"):
|
129
|
-
dashed_wrapped = first_call or est_block.dash_wrapped
|
130
|
-
dash_cls = " sk-dashed-wrapped" if dashed_wrapped else ""
|
131
|
-
out.write(f'<div class="sk-item{dash_cls}">')
|
132
|
-
|
133
|
-
if base_object_label:
|
134
|
-
_write_label_html(out, base_object_label, base_object_label_details)
|
135
|
-
|
136
|
-
kind = est_block.kind
|
137
|
-
out.write(f'<div class="sk-{kind}">')
|
138
|
-
est_infos = zip(est_block.objs, est_block.names, est_block.name_details)
|
139
|
-
|
140
|
-
for est, name, name_details in est_infos:
|
141
|
-
if kind == "serial":
|
142
|
-
_write_base_object_html(out, est, name, name_details)
|
143
|
-
else: # parallel
|
144
|
-
out.write('<div class="sk-parallel-item">')
|
145
|
-
# wrap element in a serial visualblock
|
146
|
-
serial_block = _VisualBlock("serial", [est], dash_wrapped=False)
|
147
|
-
_write_base_object_html(out, serial_block, name, name_details)
|
148
|
-
out.write("</div>") # sk-parallel-item
|
149
|
-
|
150
|
-
out.write("</div></div>")
|
151
|
-
elif est_block.kind == "single":
|
152
|
-
_write_label_html(
|
153
|
-
out,
|
154
|
-
est_block.names,
|
155
|
-
est_block.name_details,
|
156
|
-
outer_class="sk-item",
|
157
|
-
inner_class="sk-estimator",
|
158
|
-
checked=first_call,
|
159
|
-
)
|
160
|
-
|
161
|
-
|
162
|
-
_STYLE = """
|
163
|
-
#$id {
|
164
|
-
color: black;
|
165
|
-
background-color: white;
|
166
|
-
}
|
167
|
-
#$id pre{
|
168
|
-
padding: 0;
|
169
|
-
}
|
170
|
-
#$id div.sk-toggleable {
|
171
|
-
background-color: white;
|
172
|
-
}
|
173
|
-
#$id label.sk-toggleable__label {
|
174
|
-
cursor: pointer;
|
175
|
-
display: block;
|
176
|
-
width: 100%;
|
177
|
-
margin-bottom: 0;
|
178
|
-
padding: 0.3em;
|
179
|
-
box-sizing: border-box;
|
180
|
-
text-align: center;
|
181
|
-
}
|
182
|
-
#$id label.sk-toggleable__label-arrow:before {
|
183
|
-
content: "▸";
|
184
|
-
float: left;
|
185
|
-
margin-right: 0.25em;
|
186
|
-
color: #696969;
|
187
|
-
}
|
188
|
-
#$id label.sk-toggleable__label-arrow:hover:before {
|
189
|
-
color: black;
|
190
|
-
}
|
191
|
-
#$id div.sk-estimator:hover label.sk-toggleable__label-arrow:before {
|
192
|
-
color: black;
|
193
|
-
}
|
194
|
-
#$id div.sk-toggleable__content {
|
195
|
-
max-height: 0;
|
196
|
-
max-width: 0;
|
197
|
-
overflow: hidden;
|
198
|
-
text-align: left;
|
199
|
-
background-color: #f0f8ff;
|
200
|
-
}
|
201
|
-
#$id div.sk-toggleable__content pre {
|
202
|
-
margin: 0.2em;
|
203
|
-
color: black;
|
204
|
-
border-radius: 0.25em;
|
205
|
-
background-color: #f0f8ff;
|
206
|
-
}
|
207
|
-
#$id input.sk-toggleable__control:checked~div.sk-toggleable__content {
|
208
|
-
max-height: 200px;
|
209
|
-
max-width: 100%;
|
210
|
-
overflow: auto;
|
211
|
-
}
|
212
|
-
#$id input.sk-toggleable__control:checked~label.sk-toggleable__label-arrow:before {
|
213
|
-
content: "▾";
|
214
|
-
}
|
215
|
-
#$id div.sk-estimator input.sk-toggleable__control:checked~label.sk-toggleable__label {
|
216
|
-
background-color: #d4ebff;
|
217
|
-
}
|
218
|
-
#$id div.sk-label input.sk-toggleable__control:checked~label.sk-toggleable__label {
|
219
|
-
background-color: #d4ebff;
|
220
|
-
}
|
221
|
-
#$id input.sk-hidden--visually {
|
222
|
-
border: 0;
|
223
|
-
clip: rect(1px 1px 1px 1px);
|
224
|
-
clip: rect(1px, 1px, 1px, 1px);
|
225
|
-
height: 1px;
|
226
|
-
margin: -1px;
|
227
|
-
overflow: hidden;
|
228
|
-
padding: 0;
|
229
|
-
position: absolute;
|
230
|
-
width: 1px;
|
231
|
-
}
|
232
|
-
#$id div.sk-estimator {
|
233
|
-
font-family: monospace;
|
234
|
-
background-color: #f0f8ff;
|
235
|
-
border: 1px dotted black;
|
236
|
-
border-radius: 0.25em;
|
237
|
-
box-sizing: border-box;
|
238
|
-
margin-bottom: 0.5em;
|
239
|
-
}
|
240
|
-
#$id div.sk-estimator:hover {
|
241
|
-
background-color: #d4ebff;
|
242
|
-
}
|
243
|
-
#$id div.sk-parallel-item::after {
|
244
|
-
content: "";
|
245
|
-
width: 100%;
|
246
|
-
border-bottom: 1px solid gray;
|
247
|
-
flex-grow: 1;
|
248
|
-
}
|
249
|
-
#$id div.sk-label:hover label.sk-toggleable__label {
|
250
|
-
background-color: #d4ebff;
|
251
|
-
}
|
252
|
-
#$id div.sk-serial::before {
|
253
|
-
content: "";
|
254
|
-
position: absolute;
|
255
|
-
border-left: 1px solid gray;
|
256
|
-
box-sizing: border-box;
|
257
|
-
top: 2em;
|
258
|
-
bottom: 0;
|
259
|
-
left: 50%;
|
260
|
-
}
|
261
|
-
#$id div.sk-serial {
|
262
|
-
display: flex;
|
263
|
-
flex-direction: column;
|
264
|
-
align-items: center;
|
265
|
-
background-color: white;
|
266
|
-
padding-right: 0.2em;
|
267
|
-
padding-left: 0.2em;
|
268
|
-
}
|
269
|
-
#$id div.sk-item {
|
270
|
-
z-index: 1;
|
271
|
-
}
|
272
|
-
#$id div.sk-parallel {
|
273
|
-
display: flex;
|
274
|
-
align-items: stretch;
|
275
|
-
justify-content: center;
|
276
|
-
background-color: white;
|
277
|
-
}
|
278
|
-
#$id div.sk-parallel::before {
|
279
|
-
content: "";
|
280
|
-
position: absolute;
|
281
|
-
border-left: 1px solid gray;
|
282
|
-
box-sizing: border-box;
|
283
|
-
top: 2em;
|
284
|
-
bottom: 0;
|
285
|
-
left: 50%;
|
286
|
-
}
|
287
|
-
#$id div.sk-parallel-item {
|
288
|
-
display: flex;
|
289
|
-
flex-direction: column;
|
290
|
-
position: relative;
|
291
|
-
background-color: white;
|
292
|
-
}
|
293
|
-
#$id div.sk-parallel-item:first-child::after {
|
294
|
-
align-self: flex-end;
|
295
|
-
width: 50%;
|
296
|
-
}
|
297
|
-
#$id div.sk-parallel-item:last-child::after {
|
298
|
-
align-self: flex-start;
|
299
|
-
width: 50%;
|
300
|
-
}
|
301
|
-
#$id div.sk-parallel-item:only-child::after {
|
302
|
-
width: 0;
|
303
|
-
}
|
304
|
-
#$id div.sk-dashed-wrapped {
|
305
|
-
border: 1px dashed gray;
|
306
|
-
margin: 0 0.4em 0.5em 0.4em;
|
307
|
-
box-sizing: border-box;
|
308
|
-
padding-bottom: 0.4em;
|
309
|
-
background-color: white;
|
310
|
-
position: relative;
|
311
|
-
}
|
312
|
-
#$id div.sk-label label {
|
313
|
-
font-family: monospace;
|
314
|
-
font-weight: bold;
|
315
|
-
background-color: white;
|
316
|
-
display: inline-block;
|
317
|
-
line-height: 1.2em;
|
318
|
-
}
|
319
|
-
#$id div.sk-label-container {
|
320
|
-
position: relative;
|
321
|
-
z-index: 2;
|
322
|
-
text-align: center;
|
323
|
-
}
|
324
|
-
#$id div.sk-container {
|
325
|
-
/* jupyter's `normalize.less` sets `[hidden] { display: none; }`
|
326
|
-
but bootstrap.min.css set `[hidden] { display: none !important; }`
|
327
|
-
so we also need the `!important` here to be able to override the
|
328
|
-
default hidden behavior on the sphinx rendered scikit-learn.org.
|
329
|
-
See: https://github.com/scikit-learn/scikit-learn/issues/21755 */
|
330
|
-
display: inline-block !important;
|
331
|
-
position: relative;
|
332
|
-
}
|
333
|
-
#$id div.sk-text-repr-fallback {
|
334
|
-
display: none;
|
335
|
-
}
|
336
|
-
""".replace(
|
337
|
-
" ", ""
|
338
|
-
).replace(
|
339
|
-
"\n", ""
|
340
|
-
) # noqa
|
341
|
-
|
342
|
-
|
343
|
-
def _object_html_repr(base_object):
|
344
|
-
"""Build a HTML representation of a BaseObject.
|
345
|
-
|
346
|
-
Parameters
|
347
|
-
----------
|
348
|
-
base_object : base object
|
349
|
-
The BaseObject or inheritting class to visualize.
|
350
|
-
|
351
|
-
Returns
|
352
|
-
-------
|
353
|
-
html: str
|
354
|
-
HTML representation of BaseObject.
|
355
|
-
"""
|
356
|
-
with closing(StringIO()) as out:
|
357
|
-
container_id = "sk-" + str(uuid.uuid4())
|
358
|
-
style_template = Template(_STYLE)
|
359
|
-
style_with_id = style_template.substitute(id=container_id)
|
360
|
-
base_object_str = str(base_object)
|
361
|
-
|
362
|
-
# The fallback message is shown by default and loading the CSS sets
|
363
|
-
# div.sk-text-repr-fallback to display: none to hide the fallback message.
|
364
|
-
#
|
365
|
-
# If the notebook is trusted, the CSS is loaded which hides the fallback
|
366
|
-
# message. If the notebook is not trusted, then the CSS is not loaded and the
|
367
|
-
# fallback message is shown by default.
|
368
|
-
#
|
369
|
-
# The reverse logic applies to HTML repr div.sk-container.
|
370
|
-
# div.sk-container is hidden by default and the loading the CSS displays it.
|
371
|
-
fallback_msg = (
|
372
|
-
"Please rerun this cell to show the HTML repr or trust the notebook."
|
373
|
-
)
|
374
|
-
out.write(
|
375
|
-
f"<style>{style_with_id}</style>"
|
376
|
-
f'<div id={container_id!r} class="sk-top-container">'
|
377
|
-
'<div class="sk-text-repr-fallback">'
|
378
|
-
f"<pre>{html.escape(base_object_str)}</pre><b>{fallback_msg}</b>"
|
379
|
-
"</div>"
|
380
|
-
'<div class="sk-container" hidden>'
|
381
|
-
)
|
382
|
-
_write_base_object_html(
|
383
|
-
out,
|
384
|
-
base_object,
|
385
|
-
base_object.__class__.__name__,
|
386
|
-
base_object_str,
|
387
|
-
first_call=True,
|
388
|
-
)
|
389
|
-
out.write("</div></div>")
|
390
|
-
|
391
|
-
html_output = out.getvalue()
|
392
|
-
return html_output
|
1
|
+
# -*- coding: utf-8 -*-
|
2
|
+
# copyright: skbase developers, BSD-3-Clause License (see LICENSE file)
|
3
|
+
# Many elements of this code were developed in scikit-learn. These elements
|
4
|
+
# are copyrighted by the scikit-learn developers, BSD-3-Clause License. For
|
5
|
+
# conditions see https://github.com/scikit-learn/scikit-learn/blob/main/COPYING
|
6
|
+
"""Functionality to represent instance of BaseObject as html."""
|
7
|
+
|
8
|
+
import html
|
9
|
+
import uuid
|
10
|
+
from contextlib import closing
|
11
|
+
from io import StringIO
|
12
|
+
from string import Template
|
13
|
+
|
14
|
+
__author__ = ["RNKuhns"]
|
15
|
+
|
16
|
+
|
17
|
+
class _VisualBlock:
|
18
|
+
"""HTML Representation of BaseObject.
|
19
|
+
|
20
|
+
Parameters
|
21
|
+
----------
|
22
|
+
kind : {'serial', 'parallel', 'single'}
|
23
|
+
kind of HTML block
|
24
|
+
|
25
|
+
objs : list of BaseObjects or `_VisualBlock`s or a single BaseObject
|
26
|
+
If kind != 'single', then `objs` is a list of
|
27
|
+
BaseObjects. If kind == 'single', then `objs` is a single BaseObject.
|
28
|
+
|
29
|
+
names : list of str, default=None
|
30
|
+
If kind != 'single', then `names` corresponds to BaseObjects.
|
31
|
+
If kind == 'single', then `names` is a single string corresponding to
|
32
|
+
the single BaseObject.
|
33
|
+
|
34
|
+
name_details : list of str, str, or None, default=None
|
35
|
+
If kind != 'single', then `name_details` corresponds to `names`.
|
36
|
+
If kind == 'single', then `name_details` is a single string
|
37
|
+
corresponding to the single BaseObject.
|
38
|
+
|
39
|
+
dash_wrapped : bool, default=True
|
40
|
+
If true, wrapped HTML element will be wrapped with a dashed border.
|
41
|
+
Only active when kind != 'single'.
|
42
|
+
"""
|
43
|
+
|
44
|
+
def __init__(self, kind, objs, *, names=None, name_details=None, dash_wrapped=True):
|
45
|
+
self.kind = kind
|
46
|
+
self.objs = objs
|
47
|
+
self.dash_wrapped = dash_wrapped
|
48
|
+
|
49
|
+
if self.kind in ("parallel", "serial"):
|
50
|
+
if names is None:
|
51
|
+
names = (None,) * len(objs)
|
52
|
+
if name_details is None:
|
53
|
+
name_details = (None,) * len(objs)
|
54
|
+
|
55
|
+
self.names = names
|
56
|
+
self.name_details = name_details
|
57
|
+
|
58
|
+
def _sk_visual_block_(self):
|
59
|
+
return self
|
60
|
+
|
61
|
+
|
62
|
+
def _write_label_html(
|
63
|
+
out,
|
64
|
+
name,
|
65
|
+
name_details,
|
66
|
+
outer_class="sk-label-container",
|
67
|
+
inner_class="sk-label",
|
68
|
+
checked=False,
|
69
|
+
):
|
70
|
+
"""Write labeled html with or without a dropdown with named details."""
|
71
|
+
out.write(f'<div class={outer_class!r}><div class="{inner_class} sk-toggleable">')
|
72
|
+
name = html.escape(name)
|
73
|
+
|
74
|
+
if name_details is not None:
|
75
|
+
name_details = html.escape(str(name_details))
|
76
|
+
label_class = "sk-toggleable__label sk-toggleable__label-arrow"
|
77
|
+
|
78
|
+
checked_str = "checked" if checked else ""
|
79
|
+
est_id = uuid.uuid4()
|
80
|
+
out.write(
|
81
|
+
'<input class="sk-toggleable__control sk-hidden--visually" '
|
82
|
+
f'id={est_id!r} type="checkbox" {checked_str}>'
|
83
|
+
f"<label for={est_id!r} class={label_class!r}>{name}</label>"
|
84
|
+
f'<div class="sk-toggleable__content"><pre>{name_details}'
|
85
|
+
"</pre></div>"
|
86
|
+
)
|
87
|
+
else:
|
88
|
+
out.write(f"<label>{name}</label>")
|
89
|
+
out.write("</div></div>") # outer_class inner_class
|
90
|
+
|
91
|
+
|
92
|
+
def _get_visual_block(base_object):
|
93
|
+
"""Generate information about how to display a BaseObject."""
|
94
|
+
if hasattr(base_object, "_sk_visual_block_"):
|
95
|
+
return base_object._sk_visual_block_()
|
96
|
+
|
97
|
+
if isinstance(base_object, str):
|
98
|
+
return _VisualBlock(
|
99
|
+
"single", base_object, names=base_object, name_details=base_object
|
100
|
+
)
|
101
|
+
elif base_object is None:
|
102
|
+
return _VisualBlock("single", base_object, names="None", name_details="None")
|
103
|
+
|
104
|
+
# check if base_object looks like a meta base_object wraps base_object
|
105
|
+
if hasattr(base_object, "get_params"):
|
106
|
+
base_objects = []
|
107
|
+
for key, value in base_object.get_params().items():
|
108
|
+
# Only look at the BaseObjects in the first layer
|
109
|
+
if "__" not in key and hasattr(value, "get_params"):
|
110
|
+
base_objects.append(value)
|
111
|
+
if len(base_objects):
|
112
|
+
return _VisualBlock("parallel", base_objects, names=None)
|
113
|
+
|
114
|
+
return _VisualBlock(
|
115
|
+
"single",
|
116
|
+
base_object,
|
117
|
+
names=base_object.__class__.__name__,
|
118
|
+
name_details=str(base_object),
|
119
|
+
)
|
120
|
+
|
121
|
+
|
122
|
+
def _write_base_object_html(
|
123
|
+
out, base_object, base_object_label, base_object_label_details, first_call=False
|
124
|
+
):
|
125
|
+
"""Write BaseObject to html in serial, parallel, or by itself (single)."""
|
126
|
+
est_block = _get_visual_block(base_object)
|
127
|
+
|
128
|
+
if est_block.kind in ("serial", "parallel"):
|
129
|
+
dashed_wrapped = first_call or est_block.dash_wrapped
|
130
|
+
dash_cls = " sk-dashed-wrapped" if dashed_wrapped else ""
|
131
|
+
out.write(f'<div class="sk-item{dash_cls}">')
|
132
|
+
|
133
|
+
if base_object_label:
|
134
|
+
_write_label_html(out, base_object_label, base_object_label_details)
|
135
|
+
|
136
|
+
kind = est_block.kind
|
137
|
+
out.write(f'<div class="sk-{kind}">')
|
138
|
+
est_infos = zip(est_block.objs, est_block.names, est_block.name_details)
|
139
|
+
|
140
|
+
for est, name, name_details in est_infos:
|
141
|
+
if kind == "serial":
|
142
|
+
_write_base_object_html(out, est, name, name_details)
|
143
|
+
else: # parallel
|
144
|
+
out.write('<div class="sk-parallel-item">')
|
145
|
+
# wrap element in a serial visualblock
|
146
|
+
serial_block = _VisualBlock("serial", [est], dash_wrapped=False)
|
147
|
+
_write_base_object_html(out, serial_block, name, name_details)
|
148
|
+
out.write("</div>") # sk-parallel-item
|
149
|
+
|
150
|
+
out.write("</div></div>")
|
151
|
+
elif est_block.kind == "single":
|
152
|
+
_write_label_html(
|
153
|
+
out,
|
154
|
+
est_block.names,
|
155
|
+
est_block.name_details,
|
156
|
+
outer_class="sk-item",
|
157
|
+
inner_class="sk-estimator",
|
158
|
+
checked=first_call,
|
159
|
+
)
|
160
|
+
|
161
|
+
|
162
|
+
_STYLE = """
|
163
|
+
#$id {
|
164
|
+
color: black;
|
165
|
+
background-color: white;
|
166
|
+
}
|
167
|
+
#$id pre{
|
168
|
+
padding: 0;
|
169
|
+
}
|
170
|
+
#$id div.sk-toggleable {
|
171
|
+
background-color: white;
|
172
|
+
}
|
173
|
+
#$id label.sk-toggleable__label {
|
174
|
+
cursor: pointer;
|
175
|
+
display: block;
|
176
|
+
width: 100%;
|
177
|
+
margin-bottom: 0;
|
178
|
+
padding: 0.3em;
|
179
|
+
box-sizing: border-box;
|
180
|
+
text-align: center;
|
181
|
+
}
|
182
|
+
#$id label.sk-toggleable__label-arrow:before {
|
183
|
+
content: "▸";
|
184
|
+
float: left;
|
185
|
+
margin-right: 0.25em;
|
186
|
+
color: #696969;
|
187
|
+
}
|
188
|
+
#$id label.sk-toggleable__label-arrow:hover:before {
|
189
|
+
color: black;
|
190
|
+
}
|
191
|
+
#$id div.sk-estimator:hover label.sk-toggleable__label-arrow:before {
|
192
|
+
color: black;
|
193
|
+
}
|
194
|
+
#$id div.sk-toggleable__content {
|
195
|
+
max-height: 0;
|
196
|
+
max-width: 0;
|
197
|
+
overflow: hidden;
|
198
|
+
text-align: left;
|
199
|
+
background-color: #f0f8ff;
|
200
|
+
}
|
201
|
+
#$id div.sk-toggleable__content pre {
|
202
|
+
margin: 0.2em;
|
203
|
+
color: black;
|
204
|
+
border-radius: 0.25em;
|
205
|
+
background-color: #f0f8ff;
|
206
|
+
}
|
207
|
+
#$id input.sk-toggleable__control:checked~div.sk-toggleable__content {
|
208
|
+
max-height: 200px;
|
209
|
+
max-width: 100%;
|
210
|
+
overflow: auto;
|
211
|
+
}
|
212
|
+
#$id input.sk-toggleable__control:checked~label.sk-toggleable__label-arrow:before {
|
213
|
+
content: "▾";
|
214
|
+
}
|
215
|
+
#$id div.sk-estimator input.sk-toggleable__control:checked~label.sk-toggleable__label {
|
216
|
+
background-color: #d4ebff;
|
217
|
+
}
|
218
|
+
#$id div.sk-label input.sk-toggleable__control:checked~label.sk-toggleable__label {
|
219
|
+
background-color: #d4ebff;
|
220
|
+
}
|
221
|
+
#$id input.sk-hidden--visually {
|
222
|
+
border: 0;
|
223
|
+
clip: rect(1px 1px 1px 1px);
|
224
|
+
clip: rect(1px, 1px, 1px, 1px);
|
225
|
+
height: 1px;
|
226
|
+
margin: -1px;
|
227
|
+
overflow: hidden;
|
228
|
+
padding: 0;
|
229
|
+
position: absolute;
|
230
|
+
width: 1px;
|
231
|
+
}
|
232
|
+
#$id div.sk-estimator {
|
233
|
+
font-family: monospace;
|
234
|
+
background-color: #f0f8ff;
|
235
|
+
border: 1px dotted black;
|
236
|
+
border-radius: 0.25em;
|
237
|
+
box-sizing: border-box;
|
238
|
+
margin-bottom: 0.5em;
|
239
|
+
}
|
240
|
+
#$id div.sk-estimator:hover {
|
241
|
+
background-color: #d4ebff;
|
242
|
+
}
|
243
|
+
#$id div.sk-parallel-item::after {
|
244
|
+
content: "";
|
245
|
+
width: 100%;
|
246
|
+
border-bottom: 1px solid gray;
|
247
|
+
flex-grow: 1;
|
248
|
+
}
|
249
|
+
#$id div.sk-label:hover label.sk-toggleable__label {
|
250
|
+
background-color: #d4ebff;
|
251
|
+
}
|
252
|
+
#$id div.sk-serial::before {
|
253
|
+
content: "";
|
254
|
+
position: absolute;
|
255
|
+
border-left: 1px solid gray;
|
256
|
+
box-sizing: border-box;
|
257
|
+
top: 2em;
|
258
|
+
bottom: 0;
|
259
|
+
left: 50%;
|
260
|
+
}
|
261
|
+
#$id div.sk-serial {
|
262
|
+
display: flex;
|
263
|
+
flex-direction: column;
|
264
|
+
align-items: center;
|
265
|
+
background-color: white;
|
266
|
+
padding-right: 0.2em;
|
267
|
+
padding-left: 0.2em;
|
268
|
+
}
|
269
|
+
#$id div.sk-item {
|
270
|
+
z-index: 1;
|
271
|
+
}
|
272
|
+
#$id div.sk-parallel {
|
273
|
+
display: flex;
|
274
|
+
align-items: stretch;
|
275
|
+
justify-content: center;
|
276
|
+
background-color: white;
|
277
|
+
}
|
278
|
+
#$id div.sk-parallel::before {
|
279
|
+
content: "";
|
280
|
+
position: absolute;
|
281
|
+
border-left: 1px solid gray;
|
282
|
+
box-sizing: border-box;
|
283
|
+
top: 2em;
|
284
|
+
bottom: 0;
|
285
|
+
left: 50%;
|
286
|
+
}
|
287
|
+
#$id div.sk-parallel-item {
|
288
|
+
display: flex;
|
289
|
+
flex-direction: column;
|
290
|
+
position: relative;
|
291
|
+
background-color: white;
|
292
|
+
}
|
293
|
+
#$id div.sk-parallel-item:first-child::after {
|
294
|
+
align-self: flex-end;
|
295
|
+
width: 50%;
|
296
|
+
}
|
297
|
+
#$id div.sk-parallel-item:last-child::after {
|
298
|
+
align-self: flex-start;
|
299
|
+
width: 50%;
|
300
|
+
}
|
301
|
+
#$id div.sk-parallel-item:only-child::after {
|
302
|
+
width: 0;
|
303
|
+
}
|
304
|
+
#$id div.sk-dashed-wrapped {
|
305
|
+
border: 1px dashed gray;
|
306
|
+
margin: 0 0.4em 0.5em 0.4em;
|
307
|
+
box-sizing: border-box;
|
308
|
+
padding-bottom: 0.4em;
|
309
|
+
background-color: white;
|
310
|
+
position: relative;
|
311
|
+
}
|
312
|
+
#$id div.sk-label label {
|
313
|
+
font-family: monospace;
|
314
|
+
font-weight: bold;
|
315
|
+
background-color: white;
|
316
|
+
display: inline-block;
|
317
|
+
line-height: 1.2em;
|
318
|
+
}
|
319
|
+
#$id div.sk-label-container {
|
320
|
+
position: relative;
|
321
|
+
z-index: 2;
|
322
|
+
text-align: center;
|
323
|
+
}
|
324
|
+
#$id div.sk-container {
|
325
|
+
/* jupyter's `normalize.less` sets `[hidden] { display: none; }`
|
326
|
+
but bootstrap.min.css set `[hidden] { display: none !important; }`
|
327
|
+
so we also need the `!important` here to be able to override the
|
328
|
+
default hidden behavior on the sphinx rendered scikit-learn.org.
|
329
|
+
See: https://github.com/scikit-learn/scikit-learn/issues/21755 */
|
330
|
+
display: inline-block !important;
|
331
|
+
position: relative;
|
332
|
+
}
|
333
|
+
#$id div.sk-text-repr-fallback {
|
334
|
+
display: none;
|
335
|
+
}
|
336
|
+
""".replace(
|
337
|
+
" ", ""
|
338
|
+
).replace(
|
339
|
+
"\n", ""
|
340
|
+
) # noqa
|
341
|
+
|
342
|
+
|
343
|
+
def _object_html_repr(base_object):
|
344
|
+
"""Build a HTML representation of a BaseObject.
|
345
|
+
|
346
|
+
Parameters
|
347
|
+
----------
|
348
|
+
base_object : base object
|
349
|
+
The BaseObject or inheritting class to visualize.
|
350
|
+
|
351
|
+
Returns
|
352
|
+
-------
|
353
|
+
html: str
|
354
|
+
HTML representation of BaseObject.
|
355
|
+
"""
|
356
|
+
with closing(StringIO()) as out:
|
357
|
+
container_id = "sk-" + str(uuid.uuid4())
|
358
|
+
style_template = Template(_STYLE)
|
359
|
+
style_with_id = style_template.substitute(id=container_id)
|
360
|
+
base_object_str = str(base_object)
|
361
|
+
|
362
|
+
# The fallback message is shown by default and loading the CSS sets
|
363
|
+
# div.sk-text-repr-fallback to display: none to hide the fallback message.
|
364
|
+
#
|
365
|
+
# If the notebook is trusted, the CSS is loaded which hides the fallback
|
366
|
+
# message. If the notebook is not trusted, then the CSS is not loaded and the
|
367
|
+
# fallback message is shown by default.
|
368
|
+
#
|
369
|
+
# The reverse logic applies to HTML repr div.sk-container.
|
370
|
+
# div.sk-container is hidden by default and the loading the CSS displays it.
|
371
|
+
fallback_msg = (
|
372
|
+
"Please rerun this cell to show the HTML repr or trust the notebook."
|
373
|
+
)
|
374
|
+
out.write(
|
375
|
+
f"<style>{style_with_id}</style>"
|
376
|
+
f'<div id={container_id!r} class="sk-top-container">'
|
377
|
+
'<div class="sk-text-repr-fallback">'
|
378
|
+
f"<pre>{html.escape(base_object_str)}</pre><b>{fallback_msg}</b>"
|
379
|
+
"</div>"
|
380
|
+
'<div class="sk-container" hidden>'
|
381
|
+
)
|
382
|
+
_write_base_object_html(
|
383
|
+
out,
|
384
|
+
base_object,
|
385
|
+
base_object.__class__.__name__,
|
386
|
+
base_object_str,
|
387
|
+
first_call=True,
|
388
|
+
)
|
389
|
+
out.write("</div></div>")
|
390
|
+
|
391
|
+
html_output = out.getvalue()
|
392
|
+
return html_output
|