In Ruby 2.4, how do I find the earliest index of an element of an array in another array? That is, if any element of an array occurs in the other array, I want to get the first index. I thought find_index might do it, but
在Ruby 2.4中,如何找到另一个数组中数组元素的最早索引?也就是说,如果数组中的任何元素出现在另一个数组中,我想要得到第一个索引。我以为find_index可以,但是
2.4.0 :004 > a = ["a", "b", "c"]
=> ["a", "b", "c"]
2.4.0 :005 > a.find_index("a")
=> 0
2.4.0 :006 > a.find_index(["b", "c"])
=> nil
In the above example, I would expect to see the output "1" because the element "b" occurs at index 1 in the array "a".
在上面的示例中,我希望看到输出“1”,因为元素“b”出现在数组“a”中的索引1处。
4 个解决方案
#1
2
find_index
takes a single element. You could find the minimum by doing something like
find_index使用一个元素。你可以用类似的方法求出最小值
a = ["a", "b", "c"]
to_find = ["b", "c"]
to_find.map {|i| a.find_index(i) } .compact.min # => 1
#2
5
You can use Array#index
with a block.
您可以使用数组#索引和一个块。
a = ['a', 'b', 'c']
a.index { |x| ['b', 'c'].include?(x) }
#=> 1
Quote from the docs:
引用的文档:
If a block is given instead of an argument, returns the index of the first object for which the block returns true. Returns nil if no match is found.
如果给定的是一个块而不是一个参数,则返回第一个对象的索引,该块为该对象返回true。如果没有找到匹配项,返回nil。
As Cary pointed out in his comment it is not the most performant algorithm to compare all elements in a
against all element in ['b', 'c']
(this would lead to O(n*m)
). Depending on the size of both arrays if might sense to build a more efficient data structure first. Using a Set
instead of an Array has some cost in creating the set
up front, but makes the comparison in the block much faster (overall O(n+m)
):
正如Cary在他的评论中指出的那样,将a中的所有元素与['b', 'c']中的所有元素进行比较(这将导致O(n*m))并不是性能最好的算法。根据两个数组的大小,是否可以先构建一个更有效的数据结构。使用一个集合而不是一个数组在创建前面的设置中有一些成本,但是在块中进行比较的速度要快得多(整体O(n+m)):
require 'set'
a = ['a', 'b', 'c']
set = Set.new(['b', 'c'])
a.index { |x| set.include?(x) }
#=> 1
#3
0
You can use find_index
and pass the needed value from the array:
您可以使用find_index并从数组中传递所需的值:
a = ["a", "b", "c"]
p a.find_index('a')
p a.find_index('b')
p a.find_index('c')
# => 0
# => 1
# => 2
You can use map
to get every element inside your a
array and then to get the index corresponding to each element:
您可以使用map来获取数组中的每个元素,然后获取每个元素对应的索引:
p a.map{|e| a.find_index(e)}
# => [0, 1, 2]
Another possible way to handle it could be to use the Enumerable#each_with_index
:
另一种可能的处理方法是使用可枚举的#each_with_index:
a.each_with_index{|e,i| puts "Element: #{e}, Index: #{i}"}
# => Element: a, Index: 0
# => Element: b, Index: 1
# => Element: c, Index: 2
If you want to check the indexes for each element in ["b", "c"]
using the ["a", "b", "c"]
array, you can map the first one, get the array values, and then use the a,b,c
to check those indexes:
如果您想使用[a]、"b"、"c"]数组检查[b"、"b"、"c"中的每个元素的索引,您可以映射第一个元素,得到数组的值,然后使用a、b、c检查这些索引:
p ["b", "c"].map{|e| ["a", "b", "c"].find_index(e) }
# => [1, 2]
You can also see Array#index
and Enumerable#find_index
.
您还可以看到数组#index和可枚举的#find_index。
#4
0
You could find index of all elements of array b
in the array a
, and find the min index to find the index at which an element from array b
occurred first in array a
.
可以在数组a中找到数组b的所有元素的索引,找到最小索引,找到数组a中第一个元素出现的索引。
Something like below:
类似下图:
a = ["a", "b", "c"]
b = ["b", "c"]
b.map { |x| a.find_index(x) }.min
#=> 1
#1
2
find_index
takes a single element. You could find the minimum by doing something like
find_index使用一个元素。你可以用类似的方法求出最小值
a = ["a", "b", "c"]
to_find = ["b", "c"]
to_find.map {|i| a.find_index(i) } .compact.min # => 1
#2
5
You can use Array#index
with a block.
您可以使用数组#索引和一个块。
a = ['a', 'b', 'c']
a.index { |x| ['b', 'c'].include?(x) }
#=> 1
Quote from the docs:
引用的文档:
If a block is given instead of an argument, returns the index of the first object for which the block returns true. Returns nil if no match is found.
如果给定的是一个块而不是一个参数,则返回第一个对象的索引,该块为该对象返回true。如果没有找到匹配项,返回nil。
As Cary pointed out in his comment it is not the most performant algorithm to compare all elements in a
against all element in ['b', 'c']
(this would lead to O(n*m)
). Depending on the size of both arrays if might sense to build a more efficient data structure first. Using a Set
instead of an Array has some cost in creating the set
up front, but makes the comparison in the block much faster (overall O(n+m)
):
正如Cary在他的评论中指出的那样,将a中的所有元素与['b', 'c']中的所有元素进行比较(这将导致O(n*m))并不是性能最好的算法。根据两个数组的大小,是否可以先构建一个更有效的数据结构。使用一个集合而不是一个数组在创建前面的设置中有一些成本,但是在块中进行比较的速度要快得多(整体O(n+m)):
require 'set'
a = ['a', 'b', 'c']
set = Set.new(['b', 'c'])
a.index { |x| set.include?(x) }
#=> 1
#3
0
You can use find_index
and pass the needed value from the array:
您可以使用find_index并从数组中传递所需的值:
a = ["a", "b", "c"]
p a.find_index('a')
p a.find_index('b')
p a.find_index('c')
# => 0
# => 1
# => 2
You can use map
to get every element inside your a
array and then to get the index corresponding to each element:
您可以使用map来获取数组中的每个元素,然后获取每个元素对应的索引:
p a.map{|e| a.find_index(e)}
# => [0, 1, 2]
Another possible way to handle it could be to use the Enumerable#each_with_index
:
另一种可能的处理方法是使用可枚举的#each_with_index:
a.each_with_index{|e,i| puts "Element: #{e}, Index: #{i}"}
# => Element: a, Index: 0
# => Element: b, Index: 1
# => Element: c, Index: 2
If you want to check the indexes for each element in ["b", "c"]
using the ["a", "b", "c"]
array, you can map the first one, get the array values, and then use the a,b,c
to check those indexes:
如果您想使用[a]、"b"、"c"]数组检查[b"、"b"、"c"中的每个元素的索引,您可以映射第一个元素,得到数组的值,然后使用a、b、c检查这些索引:
p ["b", "c"].map{|e| ["a", "b", "c"].find_index(e) }
# => [1, 2]
You can also see Array#index
and Enumerable#find_index
.
您还可以看到数组#index和可枚举的#find_index。
#4
0
You could find index of all elements of array b
in the array a
, and find the min index to find the index at which an element from array b
occurred first in array a
.
可以在数组a中找到数组b的所有元素的索引,找到最小索引,找到数组a中第一个元素出现的索引。
Something like below:
类似下图:
a = ["a", "b", "c"]
b = ["b", "c"]
b.map { |x| a.find_index(x) }.min
#=> 1