2

如果值:

myhash['first_key']['second_key']

存在,那么我需要得到它。但'second_key'可能根本不存在,my_hash如果不是,我不希望该行抛出异常。

现在我正在用一个丑陋的条件包装整个事情,如下所示:

if myhash['first_key'].present? and myhash['first_key']['second_key'].present?
  ...
end

我敢肯定一定有更简单的东西。

4

6 回答 6

8

您可以随时使用try

hsh.try(:[], 'first_key').try(:[], 'second_key')

仅供参考:如果您要进行大量此类检查,则可能需要重构代码以避免这些情况。

于 2013-09-16T19:36:57.487 回答
4

如有疑问,请编写一个包装器:

h = {
  first_key: {
    second_key: 'test'
  }
}

class Hash
  def fetch_path(*parts)
    parts.reduce(self) do |memo, key|
      memo[key] if memo
    end
  end
end

h.fetch_path(:first_key, :second_key) # => "test"
h.fetch_path(:first_key, :third_key) # => nil
h.fetch_path(:first_key, :third_key, :fourth_key) # => nil
h.fetch_path(:foo, :third_key) # => nil
于 2013-09-16T19:47:16.837 回答
4

试试这个整洁干净的解决方案。哈希默认值:

h = Hash.new( {} ) # sets a hash as default value

现在做你喜欢的事:

h[:some_key] # => {}
h[:non_existent_key][:yet_another_non_existent_key] # => nil

好的?

假设您有一个已经填充的现有哈希:

h = { a: 1, b: 2, c: 3 }

因此,您只需将其默认设置为返回一个新的哈希:

h.default = {}

你又来了:

h[:d] # => {}
h[:d][:e] # => nil
于 2013-09-16T19:54:46.753 回答
1

我会向您指出出色的Hashie::Mash

一个例子:

mash = Hashie::Mash.new

# Note: You used to be able to do : `mash.hello.world` and that would return `nil`
# However it seems that behavior has changed and now you need to use a `!` :

mash.hello!.world # => nil  # Note use of `!`


mash.hello!.world = 'Nice'  # Multi-level assignment!


mash.hello.world # => "Nice"
# or
mash.hello!.world # => "Nice"
于 2013-09-17T06:29:27.063 回答
0

您可以在处理哈希之前设置一些默认值。就像是:

myhash[:first_key] ||= {}

if myhash[:first_key][:second_key]
  # do work
end
于 2013-09-16T19:54:38.707 回答
0

为什么不为此定义一个方法?

class Hash
  def has_second_key?(k1,k2)
    self[k1] ? self[k1][k2] : nil
  end
end
new_hash = {}
new_hash["a"] = "b"
new_hash["c"] = {"d"=>"e","f"=>"g"}
new_hash[:p] = {q:"r"}
new_hash.has_second_key?("r","p")
  # =>nil
new_hash.has_second_key?("c","f")
  # =>"g"
new_hash.hash_second_key?(:p,:q)
  # =>"r"

要修改您的代码,它将是:

if myhash.has_second_key?('first-key','second-key') 
  ...
end

该方法将返回nilRuby 中的 Falsey,或者返回第二个键的值,即 Ruby 中的 Truthy。

显然,如果您不想,您不必修改 Hash 类。您也可以将除哈希之外的方法作为参数。has_second_key?(hash,k1,k2). 然后将其称为:

has_second_key?(myhash,'first-key','second-key')
于 2013-09-16T20:09:59.743 回答