public
Last active

  • Download Gist
1-Proposal
1 2 3 4 5 6 7
Blocks are nice, but there are uses -- especially in Enumerable -- for
which the most common case seems unnecessarily verbose. What follows
is a proposed alternative convention, and a lightweight implementation
of a small part of that convention.
 
I'm interested in hearing feedback related to the convention and any
associated / hidden dangers involved.
2-ruby-1.8.5.rb
Ruby
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28
numbers = [ -2, -1, 0, 1, 2 ]
words = %w(GitHub is Logical Awesome)
 
# Summary: Everything must be passed via blocks.
 
numbers.map
# => [ -2, -1, 0, 1, 2 ]
 
numbers.map { |e| e.abs }
# => [ 2, 1, 0, 1, 2 ]
 
numbers.map { |e| e + 2 }
# => [ 0, 1, 2, 3, 4 ]
 
numbers.select { |e| e >= 0 && e < 2 }
# => [ 0, 1 ]
 
numbers.reject { |e| e.zero? }.length
# => 4
 
numbers.all? { |e| e > 0 }
# => false
 
words.map { |e| e.reverse }
# => [ 'buHtiG', 'si', 'lacigoL', 'emosewA' ]
 
words.any? { |e| e.empty? }
# => false
3-ruby-1.8.7.rb
Ruby
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29
numbers = [ -2, -1, 0, 1, 2 ]
words = %w(GitHub is Logical Awesome)
 
# Summary: Methods of arity zero can be simplified by using
# Symbol#to_proc. Blocks for everything else.
 
numbers.map
# => [ -2, -1, 0, 1, 2 ]
 
numbers.map(&:abs)
# => [ 2, 1, 0, 1, 2 ]
 
numbers.map { |e| e + 2 }
# => [ 0, 1, 2, 3, 4 ]
 
numbers.select { |e| e >= 0 && e < 2 }
# => [ 0, 1 ]
 
numbers.reject(&:zero?).length
# => 4
 
numbers.all? { |e| e > 0 }
# => false
 
words.map(&:reverse)
# => [ 'buHtiG', 'si', 'lacigoL', 'emosewA' ]
 
words.any?(&:empty?)
# => false
4-proposal.rb
Ruby
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31
numbers = [ -2, -1, 0, 1, 2 ]
words = %w(GitHub is Logical Awesome)
 
# Summary: Simple expressions can be simplified by calling
# methods on a proxy object. Complex expressions can still
# be written with a block.
 
numbers.map
# => <Proxy Object>
 
numbers.map.abs
# => [ 2, 1, 0, 1, 2 ]
 
numbers.map + 2
# => [ 0, 1, 2, 3, 4 ]
 
numbers.select { |e| e >= 0 && e < 2 }
# => [ 0, 1 ]
# Also, (numbers.select >= 0).select < 2
 
numbers.reject.zero?.length
# => 4
 
numbers.all? > 0
# => false
 
words.map.reverse
# => [ 'buHtiG', 'si', 'lacigoL', 'emosewA' ]
 
words.any?.empty?
# => false
5-implementation.rb
Ruby
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27
class Proxy
instance_methods.each { |m| undef_method m unless m =~ /^__/ }
def initialize(method, obj)
@method, @obj = method, obj
end
def method_missing(*args, &blk)
@obj.send(@method) { |e| e.send(*args, &blk) }
end
def inspect
"#{@obj.inspect}.#{@method} { |e| e.??? }"
end
end
 
class Array
alias :verbose_map :map
def map(*args, &b)
if block_given?
self.verbose_map(*args, &b)
else
Proxy.new(:map, self)
end
end
end

Please sign in to comment on this gist.

Something went wrong with that request. Please try again.