有没有办法将哈希值与迭代进行比较?

时间:2015-10-13 15:01:44

标签: ruby input hash

用户输入游戏的分数,例如"Rockets 89 Suns 91",我会根据胜利对团队进行排名,但为了知道哪个团队是胜利者,我必须比较这两个值。我可能有一个哈希:

teams = {yankees: 5, mets: 2}

我希望比较teams[:yankees]teams[:mets],但由于密钥是由用户输入的并且可能会发生变化,因此我不知道指向哪个键​​,所以我不能这样做明确地team[:yankees] <=> team[:mets]。有没有办法做到这一点?

4 个答案:

答案 0 :(得分:2)

您可以执行以下操作:

teams = { yankees: 5, mets: 2 }
max_score = teams.values.max
winning_team = teams.select { |key, value| value == max_score }
# => returns { yankees: 5 }

如果两支球队的得分相等,您可能需要添加支票。另外,考虑一下得分是否相等,你的方法是否会返回2个获胜球队或者根本没有?您的代码可能更容易处理1或0个团队,而不是1或2个获胜团队。

答案 1 :(得分:1)

不清楚你想要什么,但我想你想要获胜者名单(两队都是平局)。

当一支球队获胜时

teams = {yankees: 5, mets: 2}

teams.group_by(&:last).max.last.map(&:first) # => [:yankees]

当它是平局时

teams = {yankees: 5, mets: 5}

teams.group_by(&:last).max.last.map(&:first) # => [:yankees, :mets]

答案 2 :(得分:1)

为什么不定义处理此方法的方法:

使此代码可重复使用,您不仅可以比较游戏分数,还可以将其用于积分榜等任何其他统计信息,您可以使用相同格式的key =>value

你可以这样做:

def winner(teams)
  winners = teams.group_by(&:pop).max_by(&:shift).flatten
  if winners.count > 1 
     "It's A Tie between the #{winners.map(&:capitalize).join(' and the ')}!" 
  else
     "Winner is the #{winners.shift.capitalize}!"
  end
end

然后你可以在

中传递你的哈希
teams = {yankees: 5, mets: 3}
winner(teams)
#=> "Winner is the Yankees!"
teams[:mets] = 5
winner(teams) 
#=>  "It's A Tie between the Yankees and the Mets!"

您可以按照自己喜欢的方式比较任意数量的球队

teams = {yankees: 5, mets: 5, phillies: 5}
winner(teams)
#=> "It's A Tie between the Yankees and the Mets and the Phillies!"

如果您希望返回Array个团队,而其他人似乎认为您这样做,则修改很简单:(只需取出if语句)

def winner(teams) 
  #could also use: (same result)
  #  teams.group_by(&:pop).max.last.flatten 
  teams.group_by(&:pop).max_by(&:shift).flatten
end
teams = {yankees: 5, mets: 3} 
winner(teams)
#=> [:yankees]
teams[:mets] = 5
winner(teams)
#=> [:yankees,:mets]

如何运作

按分数对哈希进行分组(当传递给group_by时,此枚举器变为[[:yankees,5],[:mets,3]] pop,然后将分数部分拉出并按此值对团队进行分组)

teams.group_by(&:pop)
#=> {5=>[[:yankees]],3=>[[:mets]]}

然后通过键找到最大值(当传递给max_by时,这变为[[5,[[:yankees]]],[3,[[:mets]]] shift然后拉出得分部分并将其用作比较以返回团队最高分)

.max_by(&:shift)
#=>[[[:yankees]]]

然后我们展开Array

.flatten
#=> [:yankees]

答案 3 :(得分:0)

teams = {yankees: 5, mets: 2}

def compare_scores(teams)
  if teams.keys.length == 2
    return teams.values.first <=> teams.values.last
  else
    raise StandardError, "Should have exactly two teams"
  end
end

def get_winner(teams)
  result = compare_scores(teams)
  case result
    when 1
      return teams.keys.first
    when -1
      return teams.keys.last
    when 0
      return teams.keys
  end
end

compare_scores会返回&#34;&lt; =&gt;&#34;的结果两个团队的得分之间的操作员,如果有多于或少于2个团队,则提出例外。

get_winner会返回获胜者(如果有),以及两队的数组,如果他们有相同的分数。当然,您可以选择返回您想要的任何内容;)

相关问题