Project

General

Profile

Actions

Feature #16446

closed

Enumerable#take_*, Enumerable#drop_* counterparts with positive conditions

Added by sawa (Tsuyoshi Sawada) almost 5 years ago. Updated almost 5 years ago.

Status:
Rejected
Assignee:
-
Target version:
-
[ruby-core:96419]

Description

#16441 led me to think about the issue more generally. When we want to split a series of iterations by the first element that satisfies (or dissatisfies) a condition, we have three factors to consider.

(1) Whether we want the condition to work negatively or positively
(2) Whether we want the first element to satisfy (or dissatisfy) the condition to be included in the left side or the right side of the split
(3) Whether we want the left side or the right side in the returned output

This leads us to eight possible combinations to consider.

enum = [1, 1, 0, 3, 3, 0, 5, 5].to_enum
(1) (2) (3) method example
1 negatively left left take_while enum.foo1(&:nonzero?) # => [1, 1]
2 negatively left right drop_while enum.foo2(&:nonzero?) # => [0, 3, 3, 0, 5, 5]
3 negatively right left enum.foo3(&:nonzero?) # => [1, 1, 0]
4 negatively right right enum.foo4(&:nonzero?) # => [3, 3, 0, 5, 5]
5 positively left left enum.foo5(&:zero?) # => [1, 1]
6 positively left right enum.foo6(&:zero?) # => [0, 3, 3, 0, 5, 5]
7 positively right left enum.foo7(&:zero?) # => [1, 1, 0]
8 positively right right enum.foo8(&:zero?) # => [3, 3, 0, 5, 5]

Proposal #16441 asks for a method that corresponds to case 3 in the table above, but I think that would make the paradigm messy unless case 4 is also implemented. Either cases 3 and 4 should both be implemented, or both not. Actually, the current proposal is not about cases 3 and 4. I would leave that to #16641.

In many use cases (including the first example in #16641), we want to detect the "marker element" by which we split the iterations. In the cases above, that can be the element 0. In such use cases, it is more natural to describe the condition in positive terms (i.e., zero?) rather than negative terms (i.e., nonzero?). (And in other use cases, it might be the other way around.) So I would like to propose methods that correspond to cases 5, 6, 7, 8 above.

Naming of the methods should be done systematically. As a candidate, I came up with the following:

method
5 take_before
6 drop_before
7 take_upto
8 drop_upto

Related issues 1 (0 open1 closed)

Related to Ruby master - Feature #16441: Enumerable#take_while_afterRejectedActions
Actions

Also available in: Atom PDF

Like0
Like0Like0Like0Like0Like0Like0Like0Like0