Enumerables and Arrays

There's MOAR stuff there, really

Maurício Linhares / @mauriciojr

instead of !enum.all? use enum.none?


[ 1, 2, 3, 4, ].none? { |i| i > 5 }
=> true
					

use partition to divide your collection


js, others = [ 'Josh', 'Jeb', 'Terry', 'Andy' ].partition do |n|
  n.start_with?('J')
end
=> js = ["Josh", "Jeb"]
=> others = ["Terry", "Andy"]
					

you can reduce


['Josh', 'Jeb', 'Terry', 'Andy', 'John'].reduce({}) do |index,name|
  index[name[0]] ||= []
  index[name[0]] << name
  index
end
=> {"J"=>["Josh", "Jeb", "John"], "T"=>["Terry"], "A"=>["Andy"]}
					

but you can also each_with_object


['Josh', 'Jeb', 'Terry', 'Andy', 'John'].each_with_object({}) do
  |name,index|
    index[name[0]] ||= []
    index[name[0]] << name
end
=> {"J"=>["Josh", "Jeb", "John"], "T"=>["Terry"], "A"=>["Andy"]}
					

Same result as reduce but order of parameters is different.

use parens when reducing a hash


{a: [1, 4, 9], b: [2, 7, 15], c: [3, 6, 9]}.reduce({}) do
  |averages, (name,values) |
    averages[name] = values.reduce(:+)/values.size
    averages
end
=> {:a=>4, :b=>8, :c=>6}
					

use flat_map instead of map.flatten


[ [1,2,3], [5, 7, 9], [11, 12] ].flat_map do |items|
  items.find_all(&:even?) # expands to { |n| n.even? }
end
=> [2, 12]
					

be lazy

When working with large or infinite enumerables, you can't materialize them in memory, to do this, you need lazy enumerables.

using Prime numbers


Prime.lazy.select { |n| n > 100 && n < 200 }.take(10).to_a
=> [101, 103, 107, 109, 113, 127, 131, 137, 139, 149]
					

All enumerables respond to lazy

So whenever you have long operations or sequences of operations that don't need to be performed in all objects right away, use lazy.

clean up your arrays with compact


[ 1, 2, nil, 6, 7 , nil, 10 ].compact
=> [1, 2, 6, 7, 10]
					

if you have large sorted arrays, bsearch is your friend


random = Random.new(255)
sorted_items =
  (0..10_000_000).map { Random.rand(1_000_000_000)  }.sort

Benchmark.measure { sorted_items.find { |n| n == 999999864 } }
=>  0.980000   0.010000   0.990000 (  0.986976)

Benchmark.measure { sorted_items.bsearch { |n| n == 999999864 } }
=> 0.000000   0.000000   0.000000 (  0.000018)
					

yo dawg, I heard you like combinations


['Eagles', 'Phillies', '76ers', 'Flyers'].combination(3)
=> [
  ["Eagles", "Phillies", "76ers"],
  ["Eagles", "Phillies", "Flyers"],
  ["Eagles", "76ers", "Flyers"],
  ["Phillies", "76ers", "Flyers"]
]
					

and you can do permutations as well


['Eagles', 'Phillies', '76ers', 'Flyers'].permutation(3)
=> [
  ["Eagles", "Phillies", "76ers"],
  ["Eagles", "Phillies", "Flyers"],
  ["Eagles", "76ers", "Phillies"],
  ["Eagles", "76ers", "Flyers"]
  ... and many many more
]
					

randomize your array with shuffle


(1..10).to_a.shuffle
=> [9, 6, 8, 4, 7, 1, 5, 2, 10, 3]
					

use uniq to remove all duplicates from the array


[1, 1, 2, 2, 3, 3, 4, 5, 8, 8].uniq
=> [1, 2, 3, 4, 5, 8]
					

pipe your arrays


[1, 2, 3, 4] | [3, 4, 5, 6]
=> [1, 2, 3, 4, 5, 6]
					

The end

Thanks!

Maurício Linhares / @mauriciojr