Enumerable is an amazing module, and it’s a big part of what makes Ruby such a great programming language.
Enumerable gives you all sorts of cool methods like map
, select
and inject
. But my new favorite is each_cons
.
This method is really useful, you can use it to find ngrams or to check if a sequence of numbers is contiguous when combined with all?
, another Enumerable
method.
What each_cons
does is give you subarrays of size n
, so if you have [1,2,3]
, then each_cons(2)
will give you [[1,2], [2,3]]
.
Let’s see an example:

numbers = [3,5,4,2] numbers.sort.each_cons(2).all? { x,y x == y  1 } 
This code starts by sorting the numbers, then calling each_cons(2)
, which returns an Enumerator
object, and then it calls the all?
method to check if all the elements match the condition.
Here is another example, where I use each_cons
to check if a character is surrounded by the same character, like this: xyx
.

str = 'abcxyx' str.chars.each_cons(3).any? { a,b,c a == c } 
There is more!
If you wanted to know how many times this pattern occurs, instead of getting a true
/ false
result, you can just change any?
to count
.
What I find even more fascinating is the implementation for the each_cons
method.

array = [] each do element array << element array.shift if array.size > n yield array.dup if array.size == n end 
Note: This comes from the Rubinius implementation of Enumerable
. You can find the original source code here.
The implementation starts with an empty Ruby array, then it iterates through the elements using each
.
Everything is pretty standard until here. But then it adds the element to the array and it trims the array (using Array#shift) if the size is bigger than what we want. The size is the argument to each_cons
.
Then it yields a dup
of the array if the array has the requested size.
I think this is genius, because it keeps a ‘sliding window’ sort of effect into our enumerable object, instead of having to mess around with array indexes.
Wrapping Up
As you have seen, Enumerable
is a module that is worth mastering, so hop over to the documentation and see what it can do for you!
Don’t forget to share & subscribe to my newsletter in the form below if you enjoyed this article. It would help me a lot! ðŸ™‚
Related