Skip to content

Commit e7b93e7

Browse files
authored
fix #669 : made by() method of Group and Axis classes return a list of named groups
1 parent 426a058 commit e7b93e7

File tree

3 files changed

+51
-23
lines changed

3 files changed

+51
-23
lines changed

doc/source/changes/version_0_30.rst.inc

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -134,11 +134,25 @@ Miscellaneous improvements
134134
>>> people.matching(pattern='[AB]*')
135135
people['Bruce Wayne', 'Bruce Willis', 'Arthur Dent']
136136

137-
138137
* added option ``exact`` to ``join`` argument of :py:obj:`Axis.align()` and :py:obj:`LArray.align()` methods.
139138
Instead of aligning, passing ``join='exact'`` to the ``align`` method will raise an error when axes are not equal.
140139
Closes :issue:`338`.
141140

141+
* made :py:obj:`Axis.by()` and :py:obj:`Group.by()` return a list of named groups instead of anonymous groups.
142+
By default, group names are defined as ``<start>:<end>``. This can be changed via the new ``template`` argument:
143+
144+
>>> age = Axis('age=0..6')
145+
>>> age
146+
Axis([0, 1, 2, 3, 4, 5, 6], 'age')
147+
>>> age.by(3)
148+
(age.i[0:3] >> '0:2', age.i[3:6] >> '3:5', age.i[6:7] >> '6')
149+
>>> age.by(3, step=2)
150+
(age.i[0:3] >> '0:2', age.i[2:5] >> '2:4', age.i[4:7] >> '4:6', age.i[6:7] >> '6')
151+
>>> age.by(3, template='{start}-{end}')
152+
(age.i[0:3] >> '0-2', age.i[3:6] >> '3-5', age.i[6:7] >> '6')
153+
154+
Closes :issue:`669`.
155+
142156

143157
Fixes
144158
-----

larray/core/axis.py

Lines changed: 14 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -196,7 +196,7 @@ def labels(self, labels):
196196
self._labels = labels
197197
self._iswildcard = iswildcard
198198

199-
def by(self, length, step=None):
199+
def by(self, length, step=None, template=None):
200200
"""Split axis into several groups of specified length.
201201
202202
Parameters
@@ -205,6 +205,10 @@ def by(self, length, step=None):
205205
length of groups
206206
step : int, optional
207207
step between groups. Defaults to length.
208+
template : str, optional
209+
template describing how group names are generated. It is a string containing specific arguments
210+
written inside brackets {}. Available arguments are {start} and {end} representing the first and last label
211+
of each group. By default, template is defined as '{start}:{end}'.
208212
209213
Notes
210214
-----
@@ -216,15 +220,17 @@ def by(self, length, step=None):
216220
217221
Examples
218222
--------
219-
>>> age = Axis(range(10), 'age')
223+
>>> age = Axis('age=0..6')
224+
>>> age
225+
Axis([0, 1, 2, 3, 4, 5, 6], 'age')
220226
>>> age.by(3)
221-
(age.i[0:3], age.i[3:6], age.i[6:9], age.i[9:10])
222-
>>> age.by(3, 4)
223-
(age.i[0:3], age.i[4:7], age.i[8:10])
224-
>>> age.by(5, 3)
225-
(age.i[0:5], age.i[3:8], age.i[6:10], age.i[9:10])
227+
(age.i[0:3] >> '0:2', age.i[3:6] >> '3:5', age.i[6:7] >> '6')
228+
>>> age.by(3, step=2)
229+
(age.i[0:3] >> '0:2', age.i[2:5] >> '2:4', age.i[4:7] >> '4:6', age.i[6:7] >> '6')
230+
>>> age.by(3, template='{start}-{end}')
231+
(age.i[0:3] >> '0-2', age.i[3:6] >> '3-5', age.i[6:7] >> '6')
226232
"""
227-
return self[:].by(length, step)
233+
return self[:].by(length, step, template)
228234

229235
def extend(self, labels):
230236
"""

larray/core/group.py

Lines changed: 22 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -891,7 +891,7 @@ def with_axis(self, axis):
891891
"""
892892
return self.__class__(self.key, self.name, axis)
893893

894-
def by(self, length, step=None):
894+
def by(self, length, step=None, template=None):
895895
"""Split group into several groups of specified length.
896896
897897
Parameters
@@ -900,6 +900,10 @@ def by(self, length, step=None):
900900
length of new groups
901901
step : int, optional
902902
step between groups. Defaults to length.
903+
template : str, optional
904+
template describing how group names are generated. It is a string containing specific arguments
905+
written inside brackets {}. Available arguments are {start} and {end} representing the first and last label
906+
of each group. By default, template is defined as '{start}:{end}'.
903907
904908
Notes
905909
-----
@@ -912,22 +916,26 @@ def by(self, length, step=None):
912916
Examples
913917
--------
914918
>>> from larray import Axis, X
915-
>>> age = Axis(range(10), 'age')
916-
>>> age[[1, 2, 3, 4, 5]].by(2)
917-
(age[1, 2], age[3, 4], age[5])
918-
>>> age[1:5].by(2)
919-
(age.i[1:3], age.i[3:5], age.i[5:6])
920-
>>> age[1:5].by(2, 4)
921-
(age.i[1:3], age.i[5:6])
922-
>>> age[1:5].by(3, 2)
923-
(age.i[1:4], age.i[3:6], age.i[5:6])
924-
>>> X.age[[0, 1, 2, 3, 4]].by(2)
925-
(X.age[0, 1], X.age[2, 3], X.age[4])
919+
>>> age = Axis('age=0..100')
920+
>>> young_children = age[0:6]
921+
>>> young_children.by(3)
922+
(age.i[0:3] >> '0:2', age.i[3:6] >> '3:5', age.i[6:7] >> '6')
923+
>>> young_children.by(3, step=2)
924+
(age.i[0:3] >> '0:2', age.i[2:5] >> '2:4', age.i[4:7] >> '4:6', age.i[6:7] >> '6')
925+
>>> young_children.by(3, template='{start}-{end}')
926+
(age.i[0:3] >> '0-2', age.i[3:6] >> '3-5', age.i[6:7] >> '6')
926927
"""
928+
def make_group(start, length, name_template):
929+
g = self[start:start + length]
930+
labels = g.eval()
931+
g.name = name_template.format(start=labels[0], end=labels[-1]) if len(labels) > 1 else str(labels[0])
932+
return g
933+
927934
if step is None:
928935
step = length
929-
return tuple(self[start:start + length]
930-
for start in range(0, len(self), step))
936+
if template is None:
937+
template = '{start}:{end}'
938+
return tuple(make_group(start, length, template) for start in range(0, len(self), step))
931939

932940
# TODO: __getitem__ should work by label and .i[] should work by position. I guess it would be more consistent this
933941
# way even if the usefulness of subsetting a group with labels is dubious (but it is sometimes practical to treat

0 commit comments

Comments
 (0)