如何在Ruby 2.7中对哈希数组进行模式匹配?

如何在Ruby 2.7中对哈希数组进行模式匹配?,ruby,pattern-matching,ruby-2.7,Ruby,Pattern Matching,Ruby 2.7,我正在用模式匹配法对一个。我想使用它只匹配具有某些特征的数组元素。在我的例子中,有一个区域数据数组存储为散列,每个散列都有一个id。我只需要使用id为10的散列进行匹配,如下所示: require 'net/http' require 'json' HOSPITAL_DATA_URI = URI("https://www.dph.illinois.gov/sitefiles/COVIDHospitalRegions.json?nocache=1").freeze hosp

我正在用模式匹配法对一个。我想使用它只匹配具有某些特征的数组元素。在我的例子中,有一个区域数据数组存储为散列,每个散列都有一个id。我只需要使用
id
10
的散列进行匹配,如下所示:

require 'net/http'
require 'json'

HOSPITAL_DATA_URI = URI("https://www.dph.illinois.gov/sitefiles/COVIDHospitalRegions.json?nocache=1").freeze

hospital_data = JSON.parse(Net::HTTP.get(HOSPITAL_DATA_URI), symbolize_names: true)
region_values = hospital_data[:regionValues]

case region_values
  in [{id: 10, **unimportant_attributes}, **non_region_10_hashes]
    puts 'We found region 10!'
else
  puts 'aw shucks'
end

puts "...but Region 10 does exist" if region_values.find {|region| region[:id] == 10}

#=> aw shucks
#=> ...but Region 10 does exist
我希望它能打印“我们发现了10号区域!”但它没有


是否可以使用Ruby模式匹配来执行此操作?

我们发现给定的代码为
区域值检索以下值:

region_values
  #=> [
    {:region=>"Region01", :id=>1, :region_description=>"1 - Rockford Region Hospitals",
     :ICUAvail=>126, :ICUCapacity=>234, :VentsAvailable=>296, :VentsCapacity=>359},
    {:region=>"Region02", :id=>2, :region_description=>"2 - Peoria Region Hospitals",
     :ICUAvail=>140, :ICUCapacity=>304, :VentsAvailable=>398, :VentsCapacity=>496},
    {:region=>"Region03", :id=>3, :region_description=>"3 - Springfield Region Hospitals",
     :ICUAvail=>77, :ICUCapacity=>150, :VentsAvailable=>350, :VentsCapacity=>410},
    {:region=>"Region04", :id=>4, :region_description=>"4 - Edwardsville Region Hospitals",
     :ICUAvail=>61, :ICUCapacity=>113, :VentsAvailable=>134, :VentsCapacity=>158},
    {:region=>"Region05", :id=>5, :region_description=>"5 - Marion Region Hospitals",
     :ICUAvail=>64, :ICUCapacity=>107, :VentsAvailable=>294, :VentsCapacity=>309},
    {:region=>"Region06", :id=>6, :region_description=>"6 - Champaign Region Hospitals",
     :ICUAvail=>70, :ICUCapacity=>162, :VentsAvailable=>260, :VentsCapacity=>287},
    {:region=>"Region07", :id=>7, :region_description=>"7 - Southwest Suburbs Region Hospitals",
     :ICUAvail=>175, :ICUCapacity=>484, :VentsAvailable=>444, :VentsCapacity=>589},
    {:region=>"Region08", :id=>8, :region_description=>"8 - West Suburbs Region Hospitals",
     :ICUAvail=>176, :ICUCapacity=>480, :VentsAvailable=>319, :VentsCapacity=>550},
    {:region=>"Region09", :id=>9, :region_description=>"9 - Northwest Suburbs Region Hospitals",
     :ICUAvail=>238, :ICUCapacity=>452, :VentsAvailable=>438, :VentsCapacity=>533},
    {:region=>"Region10", :id=>10, :region_description=>"10 - Northeast Suburbs Region Hospitals",
     :ICUAvail=>112, :ICUCapacity=>206, :VentsAvailable=>190, :VentsCapacity=>234},
    {:region=>"Region11", :id=>11, :region_description=>"11 - City of Chicago Region Hospitals",
     :ICUAvail=>395, :ICUCapacity=>1064, :VentsAvailable=>1392, :VentsCapacity=>1803}
]
在发布这篇文章之前,我不知道Ruby v2.7中的新模式匹配功能。在阅读之后,我真的不明白这是如何应用于您的问题的(尽管该功能本身很有趣,而且似乎很有用)。你可以写:

region_values.each do |h|
  puts case h
  in {id: 10}
    'We found region 10!'
  else
    'aw shucks'
  end
end
aw shucks
aw shucks
aw shucks
aw shucks
aw shucks
aw shucks
aw shucks
aw shucks
aw shucks
We found region 10!
aw shucks

但这两个都不是新功能的有趣应用。

有答案。基本上,我正在寻找的是一种叫做“查找模式”的模式,它最近才被合并到Ruby中。预计它将出现在Ruby 3.0版本中。您将如何在我的案例中使用它:

case region\u值
#请注意“splat-like”星号。这些是“查找模式”
在[*,{id:10}=>r10,{id:11}=>r11,*]
放置“区域10:#{r10}”
放置“区域11:#{r11}”
#注意,r10和r11在这里的代码块中都可用
其他的
把“啊,胡说”
结束

因为使用这些“查找模式”非常有用。

感谢编辑Jörg,这是一次意外的复制/粘贴!是的,我想“有趣的应用程序”是我想要找到的。我真的不知道什么时候使用模式匹配。谢谢你的回答!
found = region_values.find do |h|
  case h
  in {id: 10}
    true
  end
end
puts found ? 'We found region 10!' : 'aw shucks'
We found region 10!