ruby-on-rails - 有没有一种轻量级的方法来锁定哈希上的一组 key ?

标签 ruby-on-rails ruby immutability

需要明确的是,我非常高兴自己将这个功能实现为自定义类,但我想确保我没有忽略一些 ruby​​ 或 Rails 的魔力。我用谷歌搜索了关键字“ruby Rails 哈希键值不可变锁卡住”的每一个有意义的排列。但到目前为止还没有运气!


问题:我需要为Hash提供一组键(可能在运行时),然后锁定该组键而不锁定它们的值。类似于以下内容:

to_lock = {}
to_lock[:name] = "Bill"
to_lock[:age] = 42

to_lock.freeze_keys     # <-- this is what I'm after, so that:

to_lock[:name] = "Bob"  # <-- this works fine,
to_lock[:height]        # <-- this returns nil, and
to_lock[:height] = 175  # <-- this throws some RuntimeError

问题:是否有一些 Ruby 或 Rails 工具可以实现此目的?


我知道Object#freezeImmutable::Hash ,但都锁定键值。

坚持使用开箱即用的 ruby​​,大多数用例可以通过在运行时操作类的方法或访问器来满足,如 this 中所示。或this ,然后覆盖 #method_missing 。但这感觉有点笨拙。这些技术也并没有真正“锁定”方法或访问器集,只是添加更多方法或访问器很尴尬。此时,最好简单地编写一个完全实现上面代码片段的类,并根据需要维护它。

最佳答案

您可以通过为哈希的“要锁定”实例定义自定义 []= 来实现此目的,添加允许的 key 后:

x = { name: nil, age: nil }

def x.[]=(key, value)
  # blow up unless the key already exists in the hash
  raise 'no' unless keys.include?(key)
  super
end

x[:name] # nil
x[:name] = "Bob" # "Bob"

x[:size] # nil
x[:size] = "large" # raise no

请注意,这不会阻止您使用 merge! 之类的方法无意中添加键。

关于ruby-on-rails - 有没有一种轻量级的方法来锁定哈希上的一组 key ?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39603653/

相关文章:

ruby - 如何在本地 WebServer 上执行简单的 Ruby

ruby-on-rails - 嵌套资源 - 如何避免冗余路由?

ruby-on-rails - 使用引擎时如何找到模型中的资源路径?

application.js 中 _form 部分字段的 Javascript 无法用于编辑操作

ruby - Ruby 文件删除是异步的吗?

ruby - 具有多个用户的 Sinatra App

rust - Rust 中的生命周期如何影响可变性?

javascript - 为什么我的数组在使用 slice() 后被改变了?

javascript - 我在改变 reducer 中的 redux 状态吗?

ruby-on-rails - Turbolinks 不友好?