是否可以在ruby中为to_yaml指定格式化选项?

时间:2009-06-28 11:12:28

标签: ruby yaml

代码

require 'yaml'
puts YAML.load("
is_something:
  values: ['yes', 'no']
").to_yaml

产生

--- 
is_something: 
  values: 
  - "yes"
  - "no"

虽然这是一个正确的yaml,但是当你有一个数组哈希时,它看起来很丑陋。有没有办法让to_yaml生成yaml的内联数组版本?

可以将选项哈希传递给to_yaml,但您如何使用它?

编辑0:感谢PozsárBalázs。但是,从ruby 1.8.7(2009-04-08 patchlevel 160)开始,选项哈希不像宣传的那样工作。 :(

irb
irb(main):001:0> require 'yaml'
=> true
irb(main):002:0> puts [[ 'Crispin', 'Glover' ]].to_yaml( :Indent => 4, :UseHeader => true, :UseVersion => true )
--- 
- - Crispin
  - Glover
=> nil

5 个答案:

答案 0 :(得分:10)

关于哈希选项:请参阅http://yaml4r.sourceforge.net/doc/page/examples.htm

实施例。 24:将to_yaml与选项Hash一起使用

puts [[ 'Crispin', 'Glover' ]].to_yaml( :Indent => 4, :UseHeader => true, :UseVersion => true )
# prints:
#   --- %YAML:1.0
#   -
#       - Crispin
#       - Glover

实施例。 25:选项Hash的可用符号

  

Indent:发出时使用的默认缩进(默认为2
  Separator:文档之间使用的默认分隔符(默认为'---'
  SortKeys:在发出时对哈希键进行排序? (默认为false
  UseHeader:发出时显示YAML标头? (默认为false
  UseVersion:发出时显示YAML版本? (默认为false
  AnchorFormat:发出时锚点ID的格式字符串(默认为“id%03d”)
  ExplicitTypes:发出时使用显式类型? (默认为false
  BestWidth:折叠文字时使用的字符宽度(默认为80
  UseFold:发出时强制折叠文字? (默认为false
  UseBlock:强制所有文字在发出时都是文字的? (默认为false
  Encoding:要编码的Unicode格式(默认为:Utf8;需要Iconv)

答案 1 :(得分:6)

这个丑陋的黑客似乎可以解决这个问题......

class Array
  def to_yaml_style
    :inline
  end
end

浏览ruby的源代码,我找不到任何我可以通过的选项来实现相同的目标。默认选项在lib/yaml/constants.rb

中描述

答案 2 :(得分:5)

从Ruby 1.9开始psych用作默认的YAML引擎。它支持一些属性:http://ruby-doc.org/stdlib-2.1.0/libdoc/psych/rdoc/Psych/Handler/DumperOptions.html

所以对我来说它有效:

irb(main):001:0> require 'yaml'
=> true
irb(main):002:0> puts [{'a'=> 'b', 'c'=> 'd'}, {'e'=> 'f', 'g'=>'h'}].to_yaml(:indentation => 4)
---
-   a: b
    c: d
-   e: f
    g: h

答案 3 :(得分:1)

指定输出样式只是另一个hack,但是这个允许根据特定对象自定义它,而不是全局(例如,对于所有数组)。

https://gist.github.com/jirutka/31b1a61162e41d5064fc

简单示例:

class Movie
  attr_accessor :genres, :actors

  # method called by psych to render YAML
  def encode_with(coder)
    # render array inline (flow style)
    coder['genres'] = StyledYAML.inline(genres) if genres
    # render in default style (block)
    coder['actors'] = actors if actors
  end
end

答案 4 :(得分:0)

最新版本的Ruby使用Psych模块进行YAML解析。您可以通过的选项并不多,但是可以更改缩进和线宽。查看最新的Psych documentation,了解更多详细信息。