web-dev-qa-db-fra.com

Dans Ruby, comment trouver l'index de l'un des tableaux d'éléments?

Dans Ruby 2.4, comment puis-je trouver le premier index d'un élément d'un tableau dans un autre tableau? En d’autres termes, si un élément d’un tableau apparaît dans l’autre, je souhaite obtenir le premier index. Je pensais que find_index pourrait le faire, mais

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

Dans l'exemple ci-dessus, je m'attendrais à voir la sortie "1" car l'élément "b" apparaît à l'index 1 du tableau "a".

4
user7055375

find_index prend un seul élément. Vous pouvez trouver le minimum en faisant quelque chose comme 

a = ["a", "b", "c"]
to_find = ["b", "c"]
to_find.map {|i| a.find_index(i) } .compact.min # => 1
4
Alejandro C.

Vous pouvez utiliser Array#index avec un bloc. 

a = ['a', 'b', 'c']
a.index { |x| ['b', 'c'].include?(x) }
#=> 1

Citation de la documentation:

Si un bloc est donné à la place d'un argument, renvoie l'index du premier objet pour lequel le bloc renvoie la valeur true. Renvoie la valeur nil si aucune correspondance n'est trouvée.


Comme Cary l'a fait remarquer dans son commentaire, l'algorithme le plus performant n'est pas de comparer tous les éléments de a à tous les éléments de ['b', 'c'] (cela conduirait à O(n*m)). En fonction de la taille des deux tableaux, il peut être judicieux de commencer par créer une structure de données plus efficace. L'utilisation d'une Set au lieu d'un tableau a un coût pour créer la set au début, mais rend la comparaison beaucoup plus rapide dans le bloc (O(n+m) dans son ensemble):

require 'set'

a = ['a', 'b', 'c']
set = Set.new(['b', 'c'])
a.index { |x| set.include?(x) }
#=> 1
8
spickermann

Vous pouvez utiliser find_index et transmettre la valeur requise du tableau:

a = ["a", "b", "c"]
p a.find_index('a')
p a.find_index('b')
p a.find_index('c')
# => 0
# => 1
# => 2

Vous pouvez utiliser map pour obtenir tous les éléments de votre tableau a, puis pour obtenir l'index correspondant à chaque élément:

p a.map{|e| a.find_index(e)}
# => [0, 1, 2]

Une autre façon de gérer cela pourrait être d'utiliser le Enumerable#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

Si vous souhaitez vérifier les index de chaque élément dans ["b", "c"] à l'aide du tableau ["a", "b", "c"], vous pouvez mapper le premier, obtenir les valeurs du tableau, puis utiliser le a,b,c pour vérifier ces index: 

p ["b", "c"].map{|e| ["a", "b", "c"].find_index(e) }
# => [1, 2]

Vous pouvez également voir Array#index et Enumerable#find_index .

3
Sebastian Palma

Vous pouvez trouver l'index de tous les éléments du tableau b dans le tableau a et trouver l'index min pour rechercher l'index auquel un élément du tableau b est apparu en premier dans array a.

Quelque chose comme ci-dessous:

a = ["a", "b", "c"]
b = ["b", "c"]

b.map { |x| a.find_index(x) }.min
#=> 1
0
Wand Maker