Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit0130f77

Browse files
committed
Use a dataclass instead of a dict as a return type for boxplot()
This is a prove of concept. Backward compatibility is achieved thougha collections.abc.Mapping mixin. Note though, that I did not go as faras MutableMapping. If someone has written to the returned dict, theywould still be broken.open issues:- documentation incomplete- should switch usages in the matplotlib code to attributes- Where to put the dataclass? cbook or axes?- should we use silent_list to make the repr a bit nicer?
1 parentb6f7a68 commit0130f77

File tree

7 files changed

+83
-16
lines changed

7 files changed

+83
-16
lines changed
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
``boxplot()`` returns a dataclass instead of a dict
2+
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
3+
The dataclass still supports dict-like access for backwards compatibility.

‎galleries/examples/statistics/boxplot_color.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@
2929
labels=labels)# will be used to label x-ticks
3030

3131
# fill with colors
32-
forpatch,colorinzip(bplot['boxes'],colors):
32+
forpatch,colorinzip(bplot.boxes,colors):
3333
patch.set_facecolor(color)
3434

3535
plt.show()

‎galleries/examples/statistics/boxplot_demo.py

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -108,9 +108,9 @@
108108
fig.subplots_adjust(left=0.075,right=0.95,top=0.9,bottom=0.25)
109109

110110
bp=ax1.boxplot(data,notch=False,sym='+',vert=True,whis=1.5)
111-
plt.setp(bp['boxes'],color='black')
112-
plt.setp(bp['whiskers'],color='black')
113-
plt.setp(bp['fliers'],color='red',marker='+')
111+
plt.setp(bp.boxes,color='black')
112+
plt.setp(bp.whiskers,color='black')
113+
plt.setp(bp.fliers,color='red',marker='+')
114114

115115
# Add a horizontal grid to the plot, but make it very light in color
116116
# so we can use it for reading data values but not be distracting
@@ -229,8 +229,8 @@ def fake_bootstrapper(n):
229229

230230
ax.set_xlabel('treatment')
231231
ax.set_ylabel('response')
232-
plt.setp(bp['whiskers'],color='k',linestyle='-')
233-
plt.setp(bp['fliers'],markersize=3.0)
232+
plt.setp(bp.whiskers,color='k',linestyle='-')
233+
plt.setp(bp.fliers,markersize=3.0)
234234
plt.show()
235235

236236

‎lib/matplotlib/axes/_axes.py

Lines changed: 20 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -3908,10 +3908,10 @@ def boxplot(self, x, notch=None, sym=None, vert=None, whis=None,
39083908
39093909
Returns
39103910
-------
3911-
dict
3912-
Adictionary mapping each component of the boxplot to a list
3913-
of the `.Line2D` instances created.That dictionary has the
3914-
followingkeys (assuming vertical boxplots):
3911+
BoxplotArtists
3912+
Adataclass mapping each component of the boxplot to a list
3913+
of the `.Line2D` instances created.The dataclass has the
3914+
followingattributes (assuming vertical boxplots):
39153915
39163916
- ``boxes``: the main body of the boxplot showing the
39173917
quartiles and the median's confidence intervals if
@@ -3930,6 +3930,10 @@ def boxplot(self, x, notch=None, sym=None, vert=None, whis=None,
39303930
39313931
- ``means``: points or lines representing the means.
39323932
3933+
.. versionchanged:: 3.9
3934+
Formerly, a dict was returned. The return value is now a dataclass, that
3935+
still supports dict-like access for backward-compatibility.
3936+
39333937
Other Parameters
39343938
----------------
39353939
showcaps : bool, default: :rc:`boxplot.showcaps`
@@ -4171,10 +4175,10 @@ def bxp(self, bxpstats, positions=None, widths=None, vert=True,
41714175
41724176
Returns
41734177
-------
4174-
dict
4175-
Adictionary mapping each component of the boxplot to a list
4176-
of the `.Line2D` instances created.That dictionary has the
4177-
followingkeys (assuming vertical boxplots):
4178+
BoxplotArtists
4179+
Adataclass mapping each component of the boxplot to a list
4180+
of the `.Line2D` instances created.The dataclass has the
4181+
followingattributes (assuming vertical boxplots):
41784182
41794183
- ``boxes``: main bodies of the boxplot showing the quartiles, and
41804184
the median's confidence intervals if enabled.
@@ -4184,6 +4188,10 @@ def bxp(self, bxpstats, positions=None, widths=None, vert=True,
41844188
- ``fliers``: points representing data beyond the whiskers (fliers).
41854189
- ``means``: points or lines representing the means.
41864190
4191+
.. versionchanged:: 3.9
4192+
Formerly, a dict was returned. The return value is now a dataclass, that
4193+
still supports dict-like access for backward-compatibility.
4194+
41874195
See Also
41884196
--------
41894197
boxplot : Draw a boxplot from data instead of pre-computed statistics.
@@ -4390,8 +4398,10 @@ def do_patch(xs, ys, **kwargs):
43904398

43914399
self._request_autoscale_view()
43924400

4393-
returndict(whiskers=whiskers,caps=caps,boxes=boxes,
4394-
medians=medians,fliers=fliers,means=means)
4401+
returncbook.BoxplotArtists(
4402+
whiskers=whiskers,caps=caps,boxes=boxes,
4403+
medians=medians,fliers=fliers,means=means
4404+
)
43954405

43964406
@staticmethod
43974407
def_parse_scatter_color_args(c,edgecolors,kwargs,xsize,

‎lib/matplotlib/cbook.py

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
importcollections
77
importcollections.abc
88
importcontextlib
9+
importdataclasses
910
importfunctools
1011
importgzip
1112
importitertools
@@ -19,6 +20,7 @@
1920
importtime
2021
importtraceback
2122
importtypes
23+
fromtypingimportUnion
2224
importweakref
2325

2426
importnumpyasnp
@@ -1126,6 +1128,32 @@ def _broadcast_with_masks(*args, compress=False):
11261128
returninputs
11271129

11281130

1131+
@dataclasses.dataclass(frozen=True)
1132+
classBoxplotArtists(collections.abc.Mapping):
1133+
"""
1134+
Collection of the artists created by `~.Axes.boxplot`.
1135+
1136+
For backward compatibility with the previously used dict representation,
1137+
this can alternatively be accessed like a (read-only) dict. However,
1138+
dict-like access is discouraged.
1139+
"""
1140+
boxes:Union[list["matplotlib.lines.Line2D"],list["matplotlib.patches.Patch"]]
1141+
medians:list["matplotlib.lines.Line2D"]
1142+
whiskers:list["matplotlib.lines.Line2D"]
1143+
caps:list["matplotlib.lines.Line2D"]
1144+
fliers:list["matplotlib.lines.Line2D"]
1145+
means:list["matplotlib.lines.Line2D"]
1146+
1147+
def__getitem__(self,key):
1148+
returngetattr(self,key)
1149+
1150+
def__iter__(self):
1151+
returniter(self.__annotations__)
1152+
1153+
def__len__(self):
1154+
returnlen(self.__annotations__)
1155+
1156+
11291157
defboxplot_stats(X,whis=1.5,bootstrap=None,labels=None,
11301158
autorange=False):
11311159
r"""

‎lib/matplotlib/cbook.pyi

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,13 @@
11
importcollections.abc
22
fromcollections.abcimportCallable,Collection,Generator,Iterable,Iterator
33
importcontextlib
4+
importdataclasses
45
importos
56
frompathlibimportPath
67

78
frommatplotlib.artistimportArtist
9+
frommatplotlib.linesimportLine2D
10+
frommatplotlib.patchesimportPatch
811

912
importnumpyasnp
1013
fromnumpy.typingimportArrayLike
@@ -15,6 +18,7 @@ from typing import (
1518
IO,
1619
Literal,
1720
TypeVar,
21+
Union,
1822
overload,
1923
)
2024

@@ -131,6 +135,19 @@ class GrouperView(Generic[_T]):
131135
defsimple_linear_interpolation(a:ArrayLike,steps:int)->np.ndarray: ...
132136
defdelete_masked_points(*args): ...
133137
def_broadcast_with_masks(*args:ArrayLike,compress:bool= ...)->list[ArrayLike]: ...
138+
139+
@dataclasses.dataclass
140+
classBoxplotArtists(collections.abc.Mapping):
141+
boxes:Union[list[Line2D],list[Patch]]
142+
medians:list[Line2D]
143+
whiskers:list[Line2D]
144+
caps:list[Line2D]
145+
fliers:list[Line2D]
146+
means:list[Line2D]
147+
def__getitem__(self,key:str)->Union[list[Line2D],list[Patch]]: ...
148+
def__iter__(self)->Iterator[str]: ...
149+
def__len__(self)->int: ...
150+
134151
defboxplot_stats(
135152
X:ArrayLike,
136153
whis:float|tuple[float,float]= ...,

‎lib/matplotlib/tests/test_axes.py

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3645,6 +3645,15 @@ def test_boxplot_mod_artist_after_plotting():
36453645
obj.set_color('green')
36463646

36473647

3648+
deftest_boxplot_return_dict_and_dataclass():
3649+
# check that the returned BoxplotArtists works as a dataclass and as a dict
3650+
# i.e. bp['key'] and bp.key are equivalent
3651+
fig,ax=plt.subplots()
3652+
bp=ax.boxplot(np.linspace(0,1,11),sym="o")
3653+
forkeyinbp:
3654+
assertbp[key]isgetattr(bp,key)
3655+
3656+
36483657
@image_comparison(['violinplot_vert_baseline.png',
36493658
'violinplot_vert_baseline.png'])
36503659
deftest_vert_violinplot_baseline():

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp