首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何将数字数组转换为范围

如何将数字数组转换为范围
EN

Stack Overflow用户
提问于 2013-12-30 20:42:36
回答 5查看 5.4K关注 0票数 2

我希望在Ruby中将一个带间隙的数字数组转换为一个多个范围的数组。

每个范围应确定顺序中的差距:

代码语言:javascript
复制
[1,2,3,5,6,8,9,10,11,12]

预期结果将是:

代码语言:javascript
复制
[1-3, 5-6, 8-12]

我还没有想出任何解决这个问题的好主意。我该怎么解决这个问题?

EN

回答 5

Stack Overflow用户

回答已采纳

发布于 2013-12-30 20:47:06

我将按照下面的方式使用Enumerable#slice_before

代码语言:javascript
复制
a = [1,2,3,5,6,8,9,10,11,12]
prev = a[0]
p a.slice_before { |e|
  prev, prev2 = e, prev
  prev2 + 1 != e
}.map{|b,*,c| c ? (b..c) : b }
# >> [1..3, 5..6, 8..12]
票数 8
EN

Stack Overflow用户

发布于 2013-12-31 03:42:00

代码语言:javascript
复制
a = [1,2,3,5,8,9,10,11,12]

b = [a.first-1] + (a.first..a.last).to_a - a + [a.last + 1]
  # => [0, 4, 6, 7, 13]
b.each_cons(2).with_object([]) {|(i,j), c| c << (i+1..j-1) if j > i+1}
  # => [1..3, 5..5, 8..12] 

或者,

代码语言:javascript
复制
b = [a.first] + ((a.first..a.last).to_a - a).flat_map {|e| [e-1,e+1]}+[a.last]
  # => [1, 3, 5, 5, 7, 6, 8, 12]
b.each_slice(2).map {|f,l| l >= f ? f..l : nil}.compact
  # => [1..3, 5..5, 8..12]

注:b.each_slice(2).to_a # => [[1, 3], [5, 5], [7, 6], [8, 12]]

票数 1
EN

Stack Overflow用户

发布于 2013-12-30 20:51:33

另一种解决办法是:

代码语言:javascript
复制
class Array
  def to_range_array
    res = [ Range.new(first,first) ]
    self[1..-1].sort.each{|item|
      if res.last.max == (item -1)
        res << Range.new(res.pop.min, item)
      else
        res << Range.new(item, item)
      end
    }
    res
  end
end

array =  [ 1,2,3,5,6,8,9,10,11,12 ]
p array.to_range_array #[1..3, 5..6, 8..12]

我的假设是:

  • 范围基于排序的数组。[ 9,10,11,12, 1,2,3,5,6,8]应该返回与[ 1,2,3,5,6,8,9,10,11,12 ]相同的结果。如果没有排序命令,就会得到[9..12, 1..3, 5..6, 8..8]
  • 单个值导致一个值范围(例如,8..8)。
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/20847212

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档