Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Conversation

@kddnewton
Copy link
Contributor

Implement Array#rfind, which is the same as find except from the other side of the Array. Also implemented Array#find (as opposed to the generic one on Enumerable because it is significantly faster and to keep the implementations together.

[Feature #21678]

array.c Outdated
* of the collection; returns the last element for which the block returns a
* truthy value:
*
* (0..9).find {|element| element > 2} # => 3
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The examples need to be updated

Suggested change
* (0..9).find {|element| element > 2} # => 3
* (0..9).rfind {|element| element < 5} # => 4

array.c Outdated
Comment on lines 2143 to 2145
* (0..9).find(proc {false}) {|element| element > 12} # => false
* {foo: 0, bar: 1, baz: 2}.find {|key, value| key.start_with?('b') } # => [:bar, 1]
* {foo: 0, bar: 1, baz: 2}.find(proc {[]}) {|key, value| key.start_with?('c') } # => []
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It would be better to provide examples more specific to rfind, but here's a temporary fix:

Suggested change
* (0..9).find(proc {false}) {|element| element > 12} # => false
* {foo: 0, bar: 1, baz: 2}.find {|key, value| key.start_with?('b') } # => [:bar, 1]
* {foo: 0, bar: 1, baz: 2}.find(proc {[]}) {|key, value| key.start_with?('c') } # => []
* (0..9).rfind(proc {false}) {|element| element > 12} # => false
* {foo: 0, bar: 1, baz: 2}.rfind {|key, value| key.start_with?('b') } # => [:baz, 2]
* {foo: 0, bar: 1, baz: 2}.rfind(proc {[]}) {|key, value| key.start_with?('c') } # => []


def test_rfind
ary = [1, 2, 3, 1, 2]
assert_equal(2, ary.rfind {|x| x % 2 == 0 })
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I see this test was ported from test_enum.rb, but shouldn't we add tests to verify behavior specific to rfind? This test doesn't distinguish which 2 is returned and doesn't express the difference from find.

array.c Outdated
*
* Returns the first element for which the block returns a truthy value.
*
* With a block given, calls the block with successive elements of the collection;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nitpicking: in Enumerable, it seems the word "collection" refers to the objects yielded by each method. However, I feel this word slightly off in Array. In fact, the word "collection" hardly appears at all in array.c.

As defined below, "elements" seems like a better choice.

ruby/array.c

Lines 8264 to 8265 in bec6961

* An \Array object is an ordered, integer-indexed collection of objects,
* called _elements_;

Well, since it says "collection of objects", you could say it's not incorrect, though. Also, "successive elements of the elements" may be awkward. I cannot think of a better phrase. Just for your reference.

@luke-gruber
Copy link
Contributor

I don't think you can cache idx without a bounds check in rfind because the array could be modified by the block and resized, andRARRAY_AREF doesn't do bounds checking.

Implement Array#rfind, which is the same as find except from the
other side of the Array. Also implemented Array#find (as opposed to
the generic one on Enumerable because it is significantly faster
and to keep the implementations together.

[Feature #21678]
@kddnewton
Copy link
Contributor Author

Thanks @mame and @luke-gruber — I believe I've addressed both your comments.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants