【问题标题】:JBuilder loop that produces hash产生哈希的 JBuilder 循环
【发布时间】:2013-03-31 09:19:14
【问题描述】:

我需要产生散列的循环,而不是对象数组。我有这个:

json.service_issues @service.issues do |issue|
  json.set! issue.id, issue.name
end

结果:

service_issues: [
  {
    3: "Not delivered"
  },
  {
    6: "Broken item"
  },
  {
    1: "Bad color"
  },
  {
    41: "Delivery problem"
  }
]

我需要这个:

service_issues: {
   3: "Not delivered",
   6: "Broken item",
   1: "Bad color",
   41: "Delivery problem"
}

是否可以在不手动将 AR 结果转换为哈希的情况下执行此操作?

【问题讨论】:

    标签: ruby-on-rails json jbuilder


    【解决方案1】:

    这里是 Jbuilder 开发者。

    简短的回答:是的。无需将模型数组转换为哈希即可。

    json.service_issues do
      @service.issues.each{ |issue| json.set! issue.id, issue.name }
    end
    

    但事先准备哈希可能会更容易。

    json.service_issues Hash[@service.issues.map{ |issue| [ issue.id, issue.name ] }]
    

    【讨论】:

    • @RichardCook 你不知道。 Javascript 对象键始终是字符串。因此,在 javascript 中 myObject[2] 完全等同于 myObject['2']。
    • 第一种方法的问题是,如果没有@service.issues,你不会得到一个空的散列,key 不会出现在 JSON 中(根据我的经验)。
    【解决方案2】:

    这个问题已经很老了,但是对于任何对数组(对象)的哈希感兴趣的人,您可以使用以下代码:

    @bacon_types.each do |bacon_type|
    json.set! bacon_type.name, bacon_type.bacons do |bacon|
        bacon.title bacon.title
        ...
    end
    

    【讨论】:

      【解决方案3】:

      你可以这样做

      Jbuilder.encode do |json|
        json.service_issues @service.issues.inject({}) { |hash, issue| hash[issue.id] = issue.name; hash }
      end 
      

      代码生成哈希技术可以通过下面的例子来理解。

      [1] pry(main)> array = [{id: 1, content: 'a'}, {id: 2, content: 'b'}]
      => [{:id=>1, :content=>"a"}, {:id=>2, :content=>"b"}]
      [2] pry(main)> array.inject({}) { |hash, element| hash[element[:id]] = element[:content]; hash }
      => {1=>"a", 2=>"b"}
      

      inject生成hash的关键点,每次插入新元素后返回创建的hash。上例,通过; hash实现。

      【讨论】:

        猜你喜欢
        • 2013-09-24
        • 2012-03-05
        • 2018-06-13
        • 2014-11-14
        • 1970-01-01
        • 1970-01-01
        • 2016-08-20
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多