/ Tags: RUBY-CODE / Categories: SOLUTIONS

Group Consecutive Elements In An Array By Condition In Ruby

Use chunk_while to group adjacent array elements that share a condition — perfect for run-length encoding, streak detection, and range grouping.

Description

Enumerable#chunk_while yields each consecutive pair (a, b) and groups elements into chunks as long as the block returns truthy. When the block returns false, a new chunk begins. It returns an Enumerator of arrays — each inner array is one group. Common uses: grouping consecutive integers into ranges, grouping sorted dates into streaks, run-length encoding, and partitioning data by monotonic properties.

Sample input:

  [1, 2, 3, 7, 8, 9, 15, 16]


Sample Output:

  [[1, 2, 3], [7, 8, 9], [15, 16]]

Answer

    arr = [1, 2, 3, 7, 8, 9, 15, 16]

    # Group consecutive integers (differ by 1)
    arr.chunk_while { |a, b| b == a + 1 }.to_a
    # => [[1, 2, 3], [7, 8, 9], [15, 16]]

    # Convert consecutive groups to ranges
    arr.chunk_while { |a, b| b == a + 1 }
       .map { |group| group.first..group.last }
    # => [1..3, 7..9, 15..16]

    # Group non-decreasing sequences
    [3, 1, 4, 1, 5, 9, 2, 6].chunk_while { |a, b| b >= a }.to_a
    # => [[3], [1, 4], [1, 5, 9], [2, 6]]

    # Detect login streaks from sorted dates
    dates = [Date.new(2024,1,1), Date.new(2024,1,2), Date.new(2024,1,4), Date.new(2024,1,5)]
    streaks = dates.chunk_while { |a, b| (b - a).to_i == 1 }.to_a
    # => [[2024-01-01, 2024-01-02], [2024-01-04, 2024-01-05]]
    longest_streak = streaks.max_by(&:length)

Learn More

cdrrazan

Rajan Bhattarai

Full Stack Software Developer! 💻 🏡 Grad. Student, MCS. 🎓 Class of '23. GitKraken Ambassador 🇳🇵 2021/22. Works with Ruby / Rails. Photography when no coding. Also tweets a lot at TW / @cdrrazan!

Read More