Project

General

Profile

Actions

Feature #6150

closed

add Enumerable#grep_v

Added by sunaku (Suraj Kurapati) about 12 years ago. Updated over 11 years ago.

Status:
Rejected
Target version:
[ruby-core:43313]

Description

Please add a grep_v() method to Enumerable that behaves like the opposite of grep().

For example, if Enumerable#grep() was implemented like this:

module Enumerable
def grep pattern
select {|x| pattern =~ x }
end
end

then Enumerable#grep_v() would be implemented like this (select becomes reject):

module Enumerable
def grep_v pattern
reject {|x| pattern =~ x }
end
end

The method name "grep_v" comes from the "-v" option passed to grep(1).

Thanks for your consideration.

Updated by jacksonwillis (Jackson Willis) almost 12 years ago

=begin
I think that this is a good idea.
=end

Updated by trans (Thomas Sawyer) almost 12 years ago

Can it be an option?

grep(pattern, :invert=>true)

Updated by Eregon (Benoit Daloze) almost 12 years ago

trans (Thomas Sawyer) wrote:

Can it be an option?

grep(pattern, :invert=>true)

Agreed, adding another method seems overkill (not to mention it does not look right) for such change.

Updated by sunaku (Suraj Kurapati) almost 12 years ago

Alright, then let's simplify it further because passing {:invert=>true} seems more like Rails than Ruby:

def grep(pattern, invert=false)
...
end

["hello", "world"].grep(/h/, true) # => ["world"]
["hello", "world"].grep(/h/, false) # => ["hello"]
["hello", "world"].grep(/h/) # => ["hello"]

What do you think?

Updated by rosenfeld (Rodrigo Rosenfeld Rosas) almost 12 years ago

"grep pattern, invert: true" is acceptable to me but "grep pattern, true" is not because the code becomes non readable and you'd have to check the API to understand what "true" means. This has nothing to do with Rails vs Ruby.

Updated by rosenfeld (Rodrigo Rosenfeld Rosas) almost 12 years ago

Of course, after Ruby support named parameters this could be acceptable too and I would always use it by passing the named parameter instead of just "true".

Updated by sunaku (Suraj Kurapati) almost 12 years ago

I'd rather not wait 2+ years for this issue to be resolved by making this feature dependent on Ruby 2.0's named parameters feature. I'm also not fond of passing an options hash to grep() because, although you say it has nothing to do with Ruby vs. Rails, in my limited experience with Ruby programming, it's uncommon for Ruby core API to accept options hash. In contrast, it's more common to see Rails core API accept options hash.

So I urge you to reconsider my original proposal to add a new grep_v() method. Precedents can be found throughout the FileUtils standard library:

  • ln() vs ln_s() vs ln_sf()
  • mkdir() vs mkdir_p()
  • cp() vs cp_r()
  • rm_f() vs rm_r() vs rm_rf()
  • chmod() vs chmod_R()
  • chown() vs chown_R()

Notice how these are all separate methods; they're not ln(..., :symbolic => true) and mkdir(..., :prefix => true) and so on.

Thanks for your consideration.

Updated by trans (Thomas Sawyer) almost 12 years ago

If this were for FileUtils then I'd say grep_v is acceptable. But for Enumerable grep_v is not very acceptable. Option parameters are not something only Ruby 2 does. They are very common throughout all Ruby coding, which is why Ruby 2 is going to have better support for them. The fact that Ruby's core does not often use option parameters is partly a fact that Ruby itself lags behind the application of Ruby.

Updated by now (Nikolai Weibull) almost 12 years ago

On Thu, Mar 29, 2012 at 01:14, sunaku (Suraj Kurapati) wrote:

Issue #6150 has been updated by sunaku (Suraj Kurapati).

it's uncommon for Ruby core API to accept options hash.

IO.new and IO.open now take an option Hash. I agree with your general
sentiment that it’s not consistent with the overall Ruby core API, but
most of that API was defined well before option Hashes were an
established convention.

Updated by Eregon (Benoit Daloze) almost 12 years ago

Suraj wrote:

it's uncommon for Ruby core API to accept options hash. [...]
Precedents can be found throughout the FileUtils standard library: [...]

You'll note most of these methods accept an options Hash (e.g.: rm_rf = rm_r list, options.merge(:force => true)).

Also, to add to what Thomas Sawyer said, FileUtils is a CLI(command)-like API, which Enumerable is definitely not (although likely inspired for the "grep" name).

Rodrigo Rosenfeld Rosas wrote:

Of course, after Ruby support named parameters this could be acceptable too and I would always use it by passing the named parameter instead of just "true".

Be aware that keyword arguments as implemented now (if that is what you mean) do not permit this, they just allow an easier syntax to handle arguments and some optimization:

module Enumerable
  def grep(matcher, invert: false)
    if invert
      reject { |e| matcher === e }
    else
      select { |e| matcher === e }
    end
  end
end

%w[1 2 11 22].grep(/1/) # => ["1", "11"]
%w[1 2 11 22].grep(/1/, invert: true) # => ["2", "22"]

Updated by rosenfeld (Rodrigo Rosenfeld Rosas) almost 12 years ago

Eregon (Benoit Daloze) wrote:

Rodrigo Rosenfeld Rosas wrote:

Of course, after Ruby support named parameters this could be acceptable too and I would always use it by passing the named parameter instead of just "true".

Be aware that keyword arguments as implemented now (if that is what you mean) do not permit this, they just allow an easier syntax to handle arguments and some optimization:
%w[1 2 11 22].grep(/1/) # => ["1", "11"]
%w[1 2 11 22].grep(/1/, invert: true) # => ["2", "22"]

I'm sorry, Benoit, but I didn't get it. It seems to me that they do permit. What did you mean by "they do not permit this"?

Updated by Eregon (Benoit Daloze) almost 12 years ago

Rodrigo Rosenfeld Rosas wrote:

I'm sorry, Benoit, but I didn't get it. It seems to me that they do permit. What did you mean by "they do not permit this"?

Of course, after Ruby support named parameters this could be acceptable too and I would always use it by passing the named parameter instead of just "true".

With keyword arguments, you have to pass the keyword: grep(matcher, invert: true), grep(matcher, true) is invalid (wrong number of arguments atm).

Updated by rosenfeld (Rodrigo Rosenfeld Rosas) almost 12 years ago

Oh, I see, I actually prefer this way so that I won't read code from others just passing "true". This is specially a big issue for boolean parameters as they don't mean anything by themselves.

Updated by mame (Yusuke Endoh) almost 12 years ago

  • Status changed from Open to Assigned
  • Assignee set to matz (Yukihiro Matsumoto)
  • Target version set to 2.0.0

Updated by matz (Yukihiro Matsumoto) almost 12 years ago

  • Status changed from Assigned to Rejected

We are not going to add grep_v. There's possibility of adding :invert option to grep.

Matz.

Actions

Also available in: Atom PDF

Like0
Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0Like0