在Ruby中将散列变为string

有没有办法将一个哈希平展到一个string,键和值之间的可选分隔符和键/值对?

例如, print {:a => :b, :c => :d}.flatten('=','&')应该打印a=b&c=d

我写了一些代码来做到这一点,但我想知道是否有一个更好的方法:

 class Hash def flatten(keyvaldelimiter, entrydelimiter) string = "" self.each do |key, value| key = "#{entrydelimiter}#{key}" if string != "" #nasty hack string += "#{key}#{keyvaldelimiter}#{value}" end return string end end print {:a => :b, :c => :d}.flatten('=','&') #=> 'c=d&a=b' 

谢谢

我不会覆盖已经定义的.flatten

返回一个新的数组,这个散列的一维平坦化。 也就是说,对于数组中的每个键或值,将其元素提取到新数组中。 与数组#平展不同,此方法默认情况下不会以recursion方式平展。 如果可选的级别参数确定recursion级别扁平化。

这是我知道的最简单的方法:

 {:a => 100, :b => 200}.map{|k,v| "#{k}=#{v}"}.join('&') # => "a=100&b=200" 

@ elektronaut版本的轻微变化:

你可以放一个|e| 那里代替|k, v| 在这种情况下, e是两个元素的数组,你可以调用e.join('=') 。 总之你有类似的东西

 class Hash def join(keyvaldelim=$,, entrydelim=$,) # $, is the global default delimiter map {|e| e.join(keyvaldelim) }.join(entrydelim) end end {a: 100, b: 200}.join('=', '&') # I love showing off the new Ruby 1.9 Hash syntax # => 'a=100&b=200' 

那么,你可以用标准方法和数组来做到这一点:

 class Hash def flatten(keyvaldelimiter, entrydelimiter) self.map { |k, v| "#{k}#{keyvaldelimiter}#{v}" }.join(entrydelimiter) end end 

您可能也对Rails to_query方法感兴趣。

另外,显然,你可以写成"#{k}#{keyvaldelimiter}#{v}"作为k.to_s + keyvaldelimiter + v.to_s

如果你想要生成一个URL查询string,你肯定应该使用像activesupport的to_param(别名to_query)这样的方法。 想象一下如果数据本身有和符号或等号,那么问题就出现了。

to_query负责转义:

 >> require 'active_support/core_ext/object' >> {'a&' => 'b', 'c' => 'd'}.to_query >> => "a%26=b&c=d" 

编辑

@fahadsadah关于不想加载Rails的一个很好的观点。 即使active_support / core_ext / object也会加载71个文件。 它也猴子补丁核心类。

一个轻量级和更清洁的解决

 require 'rack' # only loads 3 files {'a&' => 'b', 'c' => 'd'}.map{|pair| pair.map{|e| Rack::Utils.escape(e.to_s) }.join('=') }.join('&') # => "a%26=b&c=d" 

逃脱是重要的,否则操作是不可逆的。

不知道是否有一个内置的方式,但这里有一些较短的代码:

 class Hash def flatten(kvdelim='', entrydelim='') self.inject([]) { |a, b| a << b.join(kvdelim) }.join(entrydelim) end end puts ({ :a => :b, :c => :d }).flatten('=', '&') # => a=b&c=d 

怎么得到它在JSON格式。 这样的格式是明确的。

有很多的JSON工具的ruby。 虽然从来没有尝试过。 但是输出当然会滑入javascript等等。 可能一行。

大量的节省,虽然将在文件,因为你将需要less得多。