简体   繁体   English

红宝石each_slice具有不同的大小

[英]Ruby each_slice with different sizes

I have: 我有:

stuff = [1, 2, "a", "b", "c", "d", 4, 5, "z", "l", "m", "l", 5, 4, 4, 77]

Numbers come in groups of multiples of two, and letters come in groups of multiples of four. 数字以2的倍数为一组,字母以4的倍数为一组。

I want to group numbers in twos and letters in fours like this: 我想像这样将数字以二为一组,将字母以四为一组:

stuff_processed = [
  [1, 2],
  ["a", "b", "c", "d"],
  [4, 5], 
  ["z", "l", "m", "l"],
  [5, 4],
  [4, 77]
]

The order inside of an array that holds numbers or letters is important, the order between the arrays I do not care about. 包含数字或字母的数组内部的顺序很重要,我不在乎数组之间的顺序。

I know stuff.each_slice(2).to_a will take me part of the way. 我知道stuff.each_slice(2).to_a会让我参与其中。 I can't figure out how to get all the way to what I need though. 我无法弄清楚如何一路达到我所需要的。

stuff
.chunk(&:class)
.flat_map{|klass, a| a.each_slice(klass == Fixnum ? 2 : 4).to_a}
# => [[1, 2], ["a", "b", "c", "d"], [4, 5], ["z", "l", "m", "l"], [5, 4], [4, 77]]
arr = [1, 2, "a", "b", "c", "d", 4, 5, "z", "l", "m", "l", "s", "t",
       "u", "v", 5, 4, 4, 77, 91, 65]

H = { Fixnum=>1, String=>3 }
count = 0
arr.slice_when do |a,b|
  if a.class == b.class && count < H[a.class]
    count += 1
    false
  else
    count = 0
    true
  end
end.to_a   
  # => [[1, 2], ["a", "b", "c", "d"], [4, 5], ["z", "l", "m", "l"],
  #     ["s", "t", "u", "v"], [5, 4], [4, 77], [91, 65]] 

See Enumerable#slice_when , which first appeared in Ruby v2.2. 请参阅Enumerable#slice_when ,它首先出现在Ruby v2.2中。

This Array#conditional_slice method accepts a Block and returns an Enumerator : Array#conditional_slice方法接受一个Block并返回一个Enumerator:

stuff = [1, 2, "a", "b", "c", "d", 4, 5, "z", "l", "m", "l", 5, 4, 4, 77]

class Array
  def conditional_slice(&block)
    clone = self.dup
    Enumerator.new do |yielder|
      until clone.empty? do
        yielder << clone.shift(block_given? ? block.call(clone.first) : 1)
      end
    end
  end
end

sliced_stuff = stuff.conditional_slice{|x| x.is_a?(Numeric) ? 2 : 4}

puts sliced_stuff.to_a.inspect
# => [[1, 2], ["a", "b", "c", "d"], [4, 5], ["z", "l", "m", "l"], [5, 4], [4, 77]]

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM