gpt4 book ai didi

ruby - 如何将范围拆分为 N 个部分

转载 作者:数据小太阳 更新时间:2023-10-29 07:52:02 25 4
gpt4 key购买 nike

我想知道如何在 ruby​​ 中将一个范围拆分为 N 个部分,同时将它们添加到一个散列中,每个范围生成的值从零开始。

例如:

range = 1..60
p split(range, 4)
#=> {1..15 => 0, 16..30 => 1, 31..45 => 2, 46..60 => 3}

我读过 How to return a part of an array in Ruby?有关如何将范围切片为数组的信息,以及其他一些有关如何将切片转换回范围的信息,但我似乎无法将所有部分拼凑在一起以创建我想要的方法。

感谢帮助

最佳答案

range = 1..60

range.each_slice(range.last/4).with_index.with_object({}) { |(a,i),h|
h[a.first..a.last]=i }
#=> {1..15=>0, 16..30=>1, 31..45=>2, 46..60=>3}

步骤如下:

enum0 = range.each_slice(range.last/4)
#=> range.each_slice(60/4)
# #<Enumerator: 1..60:each_slice(15)>

您可以将此枚举器转换为数组以查看它将生成并传递给 each_with_index 的 (4) 个元素:

enum0.to_a
#=> [[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15],
# [16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30],
# [31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45],
# [46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60]]

enum1 = enum0.with_index
#=> #<Enumerator: #<Enumerator: 1..60:each_slice(15)>:with_index>
enum1.to_a
#=> [[[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15], 0],
# [[16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30], 1],
# [[31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45], 2],
# [[46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60], 3]]

enum2 = enum1.with_object({})
#=> #<Enumerator: #<Enumerator: #<Enumerator: 1..60:each_slice(15)>
# :with_index>:with_object({})>
enum2.to_a
#=> [[[[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15], 0], {}],
# [[[16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30], 1], {}],
# [[[31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45], 2], {}],
# [[[46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60], 3], {}]]

仔细检查 enum1enum2 计算的返回值。您可能希望将它们视为“复合”枚举器。 enum2 的四个数组中的每一个的第二个和最后一个元素是由 block 变量 h 表示的空散列。该散列将在后续计算中构建。

enum2.each { |(a,i),h| h[a.first..a.last]=i }
#=> {1..15=>0, 16..30=>1, 31..45=>2, 46..60=>3}

each 传递给 block 的 enum2 的第一个元素(在执行 enum.each... 之前)是

arr = enum2.next
#=>[[[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15], 0], {}]

block 变量使用并行赋值(有时称为多重赋值)赋值给arr的元素

(a,i),h = arr
#=> [[[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15], 0], {}]
a #=> [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15]
i #=> 0
h #=> {}

block 计算因此

h[a.first..a.last]=i 
#=> h[1..15] = 0

现在

h #=> {1..15=>0} 

对于由 enum2 生成的其他 3 个元素中的每一个,计算都是类似的。

表达式

enum2.each { |(a,i),h| h[(a.first..a.last)]=i }

也可以这样写

enum2.each { |((f,*_,l),i),h| h[(f..l)]=i }

关于ruby - 如何将范围拆分为 N 个部分,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/37514671/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com