Slide 1

Slide 1 text

ENumerators

Slide 2

Slide 2 text

Enumerable #all? #any? #chunk #collect #collect_concat #count #cycle #detect #drop #drop_while #each_cons #each_entry #each_slice #each_with_index #each_with_object #entries #find #find_all #find_index #first #flat_map #grep #group_by #include? #inject #lazy #map #max #max_by #min_by #minmax #minmax_by #none? #one? #partition #reduce #reject #reverse_each #select #slice_before #sort #sort_by #take #take_while #to_a #zip

Slide 3

Slide 3 text

Enumerator #each #feed #next #next_values #peek #peek_values #rewind #size #with_index #with_object

Slide 4

Slide 4 text

enumerator = [1, 2, 3].each # => # enumerator = [1, 2, 3].to_enum # => # enumerator = [1, 2, 3].enum_for(:each) # => #

Slide 5

Slide 5 text

def counter yield 1 yield 2 yield 3 end enumerator = enum_for(:counter) enumerator.to_a # => [1, 2, 3]

Slide 6

Slide 6 text

with_object with_index

Slide 7

Slide 7 text

letters = ['a', 'a', 'a', 'b', 'b', 'c'] counts = letters.inject({}) do |memo, letter| memo[letter] ||= 0 memo[letter] += 1 memo end # => {"a"=>3, "b"=>2, "c"=>1}

Slide 8

Slide 8 text

letters = ['a', 'a', 'a', 'b', 'b', 'c'] counts = letters.each.with_object({}) do |letter, memo| memo[letter] ||= 0 memo[letter] += 1 end # => {"a"=>3, "b"=>2, "c"=>1}

Slide 9

Slide 9 text

range = (1..10) range.map.with_index {|n, i| n * i } # => [0, 2, 6, 12, 20, 30, 42, 56, 72, 90] range.select.with_index {|_, i| i.even? } # => [1, 3, 5, 7, 9]

Slide 10

Slide 10 text

Iterator

Slide 11

Slide 11 text

enumerator = [1, 2, 3].each # => # enumerator.next # => 1 enumerator.next # => 2 enumerator.next # => 3 enumerator.next # StopIteration: iteration reached an end

Slide 12

Slide 12 text

enumerator = [1, 2, 3].to_enum # => # enumerator.peek # => 1 enumerator.peek # => 2 enumerator.peek # => 3 enumerator.next # => 1

Slide 13

Slide 13 text

loop do i = enumerator.next puts i # `loop` silently rescues StopIteration end

Slide 14

Slide 14 text

Generator

Slide 15

Slide 15 text

fibonacci = Enumerator.new(Float::INFINITY) do |yielder| a, b = 0, 1 loop do yielder.yield a a, b = b, (a + b) end end

Slide 16

Slide 16 text

class SumOfNaturalNumbers < Enumerator def initialize super(Float::INFINITY) do |yielder| n = 1 loop do yielder.yield (n * (n + 1)) / 2 n += 1 end end end end

Slide 17

Slide 17 text

def fibonacci a, b = 0, 1 loop do yield a a, b = b, (a + b) end end enumerator = enum_for(:fibonacci) # => #

Slide 18

Slide 18 text

LAZY

Slide 19

Slide 19 text

require 'prime' primes = Prime.instance primes .select {|i| i.to_s.end_with?('3') } .take(10) # infinite loop

Slide 20

Slide 20 text

require 'prime' primes = Prime.instance primes .lazy .select {|i| i.to_s.end_with?('3') } .take(10) .to_a # => [3, 13, 23, 43, 53, 73, 83, 103, 113, 163]

Slide 21

Slide 21 text

File.open('/usr/share/dict/words') .each_line .lazy .map(&:chomp) .take_while {|line| line.length < 10 } .to_a

Slide 22

Slide 22 text

mine = ->(repository) { repository.owner == 'olly' } cutoff = (Time.now - (365 * 24 * 60 * 60)).to_datetime year_old = ->(repository) { repository.commits.first.date > cutoff } client.repositories .lazy .select(&mine) .select(&year_old) .take(10) .each {|repository| puts repository.name }