Ruby 数组元素的索引

3

假设我有一个整数数组,我想要找到其中一个长重复数字序列开始的索引。

my_array = [100, 101, 100, 102, 100, 100, 101, 100, 250, 251, 253, 260, 250, 200, 100, 100, 100, 100, 100, 100, 100, 100, 100, 120]

以下是我正在尝试查找索引的方法。有没有人能建议更优化和正确的做法?
my_array.each with_index do |e, x|
  match = e.to_s * 5
  next_10 = my_array[x + 1, 5].join()

  if match == next_10
    puts "index #{x}"
    break
  end
end

#index 14

1
你对数组规范化的定义是什么? - ray
1
@Aparichith “same elements starts appearing” 这个说法有点含糊不清。几乎听起来像是“你看到时就会知道”。请更具体一些。 - Stefan
@Stefan 我们可以定义一个函数来找到最长重复数字序列的起始索引,但是它没有进行标准化定义。 - ray
有没有人能够建议我一种更加正确的方法?你的方式存在什么问题吗? - Stefan
我已经更新了问题。 - Aparichith
显示剩余2条评论
4个回答

2
my_array.index.with_index{|value,index| my_array[index,6].uniq.size==1}

如果你指的是代码看起来“优化”了,那么这是一种微调。但如果你指的是性能优化,那么就不适用。


你能详细说明一下数字6在这里是如何工作的吗?似乎它不适用于其他整数的组合。 - Oshan Wisumperuma
问题已经更改。此答案基于演示代码。 - Pengcheng Zhou

1
在第一次迭代中,我获取重复元素序列的数组,然后使用逻辑进行进一步处理。
groups = my_array[1..-1].inject([[my_array[0]]]) { |m, n| m.last[0] == n ? m.last << n : m << [n]; m }
# => [[100], [101], [100], [102], [100, 100], [101], [100], [250], [251], [253], [260], [250], [200], [100, 100, 100, 100, 100, 100, 100, 100, 100], [120]]

groups[0,groups.index(groups.sort { |a,b| a.count <=> b.count }.last)].flatten.count
# => 14

使用正则表达式,可以精确而简单地实现。

1
my_array = [100, 101, 100, 102, 100, 100, 101, 100, 250, 251, 253, 260, 250, 200, 100, 100, 100, 100, 100, 100, 100, 100, 100, 120]


index_and_repetitions = lambda { |my_array|
  stk = {}
  previous = my_array[0]
  last_index = 0
  stk[last_index] = 1
  my_array.drop(0).each_with_index{|item, index|
    if item == previous
      stk[last_index] += 1
    else
      last_index = index
      stk[last_index] = 1
      previous = item
    end
  }
  stk
}

stk = index_and_repetitions.call(my_array)
puts stk.key(stk.values.max)

您可以从这里找到基准测试结果(与其他答案相比)


1
我假设目标是在给定的数组中找到相等元素最长序列的第一个元素的索引。
my_array = [100, 101, 100, 102, 100, 100, 101, 100, 250, 251, 253, 260, 250, 200,
            100, 100, 100, 100, 100, 100, 100, 100, 100,
            120]

这里是14,是后面还有8个100100的索引。

我们可以按照以下方式进行操作。

my_array.each_index.chunk { |i| my_array[i] }.
         max_by { |_,a| a.size }.
         last.
         first
           #=> 14

步骤如下:

enum0 = my_array.each_index
  #=> #<Enumerator: [100, 101, 100,..., 100, 120]:each_index> 

我们可以通过将此枚举器转换为数组来查看将生成的元素。
enum0.to_a
  #=> [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16,
  #    17, 18, 19, 20, 21, 22, 23]

继续,
enum1 = enum0.chunk { |i| my_array[i] }
  #=> #<Enumerator: #<Enumerator::Generator:0x000058d8d09ec8a0>:each> 

考虑到上述表达式的返回值,enum1 可以被视为一个 复合枚举器,尽管 Ruby 没有这样的概念。让我们看看 enum1 将生成哪些值。
enum1.to_a
  #=> [[100, [0]], [101, [1]], [100, [2]], [102, [3]], [100, [4, 5]],
  #    [101, [6]], [100, [7]], [250, [8]], [251, [9]], [253, [10]],
  #    [260, [11]], [250, [12]], [200, [13]],
  #    [100, [14, 15, 16, 17, 18, 19, 20, 21, 22]],
  #    [120, [23]]]

继续,
a = enum1.max_by { |v,a| a.size }
  #=> [100, [14, 15, 16, 17, 18, 19, 20, 21, 22]]

作为代码块中未使用 v 的变量,该表达式通常应该写成:
a = enum1.max_by { |_,a| a.size }

下划线的存在(作为有效的局部变量)告诉读者该块变量在块计算中未被使用。最后两步如下所示。

b = a.last
  #=> [14, 15, 16, 17, 18, 19, 20, 21, 22] 
b.first
  #=> 14 

请参见 Enumerable#chunk Enumerable#max_by


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接