Skip to content

Instantly share code, notes, and snippets.

@enchf
Last active July 31, 2018 22:00
Show Gist options
  • Save enchf/a954bd71baf0b18a4fe26b0e0f3aaf7a to your computer and use it in GitHub Desktop.
Save enchf/a954bd71baf0b18a4fe26b0e0f3aaf7a to your computer and use it in GitHub Desktop.
Implementation of a Flatten function in Ruby
# This gist shows two different implementation of a Flatten function in Ruby.
# The workaround is to do something like the Deep-First Search algorithm to 'visit' all items contained in recursive arrays.
# These items are being added to the returning array after visited.
# First implementation: Recursive.
# The function tests if the object passed as argument is an array.
# If it does, it iterates it recursively, otherwise it adds the element to the visited elements array (acc).
def recursive_flatten(obj, acc = [])
obj.is_a?(Array) ? obj.each { |i| recursive_flatten(i, acc) } : acc << obj
acc
end
# Second implementation: Non-recursive.
# Original array is iterated as a stack.
# If an array is found during the iteration, is placed at the front of the stack.
# Iteration ends when stack is empty.
def non_recursive_flatten(array)
flat = []
stack = array.map(&:itself)
until stack.empty?
item = stack.shift
item.is_a?(Array) ? item.reverse_each { |i| stack.unshift(i) } : flat << item
end
flat
end
# Test method.
if $PROGRAM_NAME == __FILE__
samples = [
[1,2,3],
[1,[2,3],4,5,[6,[7,8],9,[10],[11,[12]],13],14],
[[1,2],[3,4,5],[],[6,7]],
]
p samples.map(&method(:recursive_flatten))
p samples.map(&method(:non_recursive_flatten))
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment