在YAML中,如何在多行中断字符串?

jjk*_*ker 1388 string syntax yaml

在YAML中,我有一个非常长的字符串.我想将它保留在我的编辑器的80列(或左右)视图中,所以我想打破字符串.这是什么语法?

换句话说,我有这个:

Key: 'this is my very very very very very very long string'
Run Code Online (Sandbox Code Playgroud)

我想要这个(或者这个效果):

Key: 'this is my very very very ' +
     'long string'
Run Code Online (Sandbox Code Playgroud)

我想使用上面的引号,所以我不需要在字符串中转义任何东西.

Ste*_*ett 3109

在YAML中编写多行字符串的方法有5 6 NINE(或63*,具体取决于您的计算方式).

TL; DR

块标量样式(>,|)

这些允许使用\"不转义等字符,并\n在字符串末尾添加一个新行().

> 折叠样式删除字符串中的单个换行符(但最后添加一个换行符,并将双换行符转换为单个换行符):

Key: >
  this is my very very very
  long string
Run Code Online (Sandbox Code Playgroud)

this is my very very very long string\n

| 文字样式将字符串中的每个换行符转换为文字换行符,并在最后添加一个换行符:

Key: |
  this is my very very very 
  long string
Run Code Online (Sandbox Code Playgroud)

this is my very very very\nlong string\n

这是YAML Spec 1.2的官方定义

标量内容可以用块表示法编写,使用文字样式(用"|"表示),其中所有换行符都很重要.或者,它们可以用折叠样式(用">"表示)写入,其中每个换行符折叠到一个空格,除非它结束空行或更多缩进行.

与块咬食指示器块样式(>-,|-,>+,|+)

您可以\n\n通过添加块chomping指示符来控制字符串中最后一个新行的处理,以及任何尾随空白行():

  • >,|:"clip":保持换行,删除尾随空白行.
  • >-,|-:"strip":删除换行符,删除尾随空白行.
  • >+,|+:"保持":保持换行,保持尾随空行.

"流"标样式(, ",')

它们具有有限的转义,并构造一个没有换行符号的单行字符串.它们可以与键在同一行开始,或者首先使用其他换行符.

普通样式(没有转义,没有#:组合,第一个字符的限制):

Key: this is my very very very 
  long string
Run Code Online (Sandbox Code Playgroud)

双引号样式(\并且"必须通过转义\,换行符可以使用文字\n序列插入,行可以连接而不带尾随空格\):

Key: "this is my very very \"very\" loooo\
  ng string.\n\nLove, YAML."
Run Code Online (Sandbox Code Playgroud)

"this is my very very \"very\" loooong string.\n\nLove, YAML."

单引号样式(文字'必须加倍,没有特殊字符,可能对表示以双引号开头的字符串有用):

Key: 'this is my very very "very"
  long string, isn''t it.'
Run Code Online (Sandbox Code Playgroud)

"this is my very very \"very\" long string, isn't it."

摘要

在这张表中,_意思是space character.\n表示"换行符"(\n在JavaScript中),除了"内联换行符"行,其中字面意思是反斜杠和n).

                      >     |            "     '     >-     >+     |-     |+
-------------------------|------|-----|-----|-----|------|------|------|------  
Trailing spaces   | Kept | Kept |     |     |     | Kept | Kept | Kept | Kept
Single newline => | _    | \n   | _   | _   | _   | _    |  _   | \n   | \n
Double newline => | \n   | \n\n | \n  | \n  | \n  | \n   |  \n  | \n\n | \n\n
Final newline  => | \n   | \n   |     |     |     |      |  \n  |      | \n
Final dbl nl's => |      |      |     |     |     |      | Kept |      | Kept  
In-line newlines  | No   | No   | No  | \n  | No  | No   | No   | No   | No
Spaceless newlines| No   | No   | No  | \   | No  | No   | No   | No   | No 
Single quote      | '    | '    | '   | '   | ''  | '    | '    | '    | '
Double quote      | "    | "    | "   | \"  | "   | "    | "    | "    | "
Backslash         | \    | \    | \   | \\  | \   | \    | \    | \    | \
" #", ": "        | Ok   | Ok   | No  | Ok  | Ok  | Ok   | Ok   | Ok   | Ok
Can start on same | No   | No   | Yes | Yes | Yes | No   | No   | No   | No
line as key       |
Run Code Online (Sandbox Code Playgroud)

例子

注意"空格"之前的行上的尾随空格.

- >
  very "long"
  'string' with

  paragraph gap, \n and        
  spaces.
- | 
  very "long"
  'string' with

  paragraph gap, \n and        
  spaces.
- very "long"
  'string' with

  paragraph gap, \n and        
  spaces.
- "very \"long\"
  'string' with

  paragraph gap, \n and        
  s\
  p\
  a\
  c\
  e\
  s."
- 'very "long"
  ''string'' with

  paragraph gap, \n and        
  spaces.'
- >- 
  very "long"
  'string' with

  paragraph gap, \n and        
  spaces.

[
  "very \"long\" 'string' with\nparagraph gap, \\n and         spaces.\n", 
  "very \"long\"\n'string' with\n\nparagraph gap, \\n and        \nspaces.\n", 
  "very \"long\" 'string' with\nparagraph gap, \\n and spaces.", 
  "very \"long\" 'string' with\nparagraph gap, \n and spaces.", 
  "very \"long\" 'string' with\nparagraph gap, \\n and spaces.", 
  "very \"long\" 'string' with\nparagraph gap, \\n and         spaces."
]
Run Code Online (Sandbox Code Playgroud)

使用缩进指示符阻止样式

如果以上情况对您来说还不够,您可以添加" 块缩进指示器 "(在块阻塞指示器之后,如果有的话):

- >8
        My long string
        starts over here
- |+1
 This one
 starts here
Run Code Online (Sandbox Code Playgroud)

附录

如果您在折叠样式的非第一行的开头插入额外的空格,它们将被保留,并带有奖励换行符.流样式不会发生这种情况:

- >
    my long
      string
- my long
    string
Run Code Online (Sandbox Code Playgroud)

["my long\n string\n", "my long string"]

我甚至不能.

*2个块样式,每个样式有2个可能的块阻塞指示符(或者没有),并且有9个可能的缩进指示符(或者没有),1个简单样式和2个引用样式:2 x(2 + 1)x(9 + 1)+ 1 + 2 = 63

一些信息也被归纳在这里.

  • 相反,@ wvxvw,我认为YAML是许多常见用例(例如配置文件)的最差格式,尤其是因为大多数人都被其明显的简单性所吸引,只是为了很晚才意识到它是一种非常复杂的格式.YAML做错了_look_ right - 例如,一个无害的冒号`:`在一个字符串数组中的一个字符串中使YAML将它解释为一个对象数组.它违反了[最不惊讶的原则](https://en.wikipedia.org/wiki/Principle_of_least_astonishment). (34认同)
  • 在63种语法中,你认为有一种语法允许你在多行中拼写一个不应该有换行符或空格的字符串吗?我的意思是在大多数编程语言中用"..."+"..."来写,或者在Bash中换行之前反斜杠. (27认同)
  • 又一个多行字符串语法 (27认同)
  • @pepoluan我尝试了所有可能的组合,发现只有一个允许无空间连接:在字符串周围加上双引号,在换行符之前加上反斜杠(和缩进).例如:data:text/plain; base64,dGVzdDogImZvb1wKICBiYXIiCg == (20认同)
  • 有人建立了一个关于这个主题的网站:http://yaml-multiline.info/@SteveBennettㄹ如果您不知道,请检查该页面的页脚. (17认同)
  • 我不断地回到这个答案,而且数字每次都在增加。 (4认同)
  • @Tobia你能举一个"无空间串联"的例子吗?我无法理解`示例:data:text/plain; base64,dGVzdDogImZvb1wKICBiYXIiCg ==` (3认同)
  • @jeffreyveon这只是通过注释系统的局限性共享文本文字片段的一种方法。这是一个数据URI,您只需将其粘贴到浏览器的地址栏中即可。 (3认同)
  • 最终,这是组织我见过的结构化数据最好的格式!我认为,答案很严重,但是缺少YAML解析器实现的列表以及它们支持的功能。以我的经验,大多数人根本不支持断行指示器,但是它们处理它们的方式是不同的。 (2认同)
  • @VickyChijwani我们迷失了翻译。我的评论是讽刺的,但是讽刺的翻译不好。我非常同意你的看法。 (2认同)
  • @wvxvw 抱歉,是的,我也发现以书面形式表达讽刺很棘手。尤其是在这种情况下,因为我认识的人确实_确实_认为 YAML 是一种很棒的格式:)。干杯! (2认同)
  • @VickyChijwani是的,我不确定YAML是否比XML更差,但是已经接近了。每次我配置不正确时,都是由于YAML中的某些混乱。否则我的空间不正确。如果我使用的不是超级YAML友好的编辑器,则必须用放大镜看屏幕。 (2认同)
  • 我总是很难记住“ |”中的哪个 或'>'保留或删除换行符。在某个时候,我意识到,如果从左到右读取,运算符将告诉您如何转换字符串。'|' 两侧的高度相同,这意味着琴弦也将保持相同的高度;而'>'在右侧小于在左侧,这意味着它将把字符串从多行压缩到仅一行。只是想将这些助记符留在这里,供那些尚未发现的助记符使用。 (2认同)
  • YAML 规范目标#7:“YAML 应该易于实现和使用。” 简单实现就这么多了...... (2认同)

Mat*_*son 849

使用yaml折叠样式,每个换行符由空格替换.每行中的缩进将被忽略.最后会插入换行符.

Key: >
  This is a very long sentence
  that spans several lines in the YAML
  but which will be rendered as a string
  with only a single carriage return appended to the end.
Run Code Online (Sandbox Code Playgroud)

http://symfony.com/doc/current/components/yaml/yaml_format.html

您可以使用"块阻塞指示符"来消除尾随换行符,如下所示:

Key: >-
  This is a very long sentence
  that spans several lines in the YAML
  but which will be rendered as a string
  with NO carriage returns.
Run Code Online (Sandbox Code Playgroud)

还有其他控制工具可用(例如,用于控制压痕).

请参阅https://yaml-multiline.info/

  • 答案很好,但马特威廉姆森的答案应该是公认的答案. (13认同)
  • _每个换行符都被空格代替_ <-- 但双换行符将是一个换行符。 (8认同)
  • @TravisBear *“这个答案很好,但是下面的Matt Williamson答案应该被接受。” *这是什么意思?“这个答案”是马特·威廉姆森的答案。您是说[史蒂夫·贝内特的答案](/sf/ask/265331811/#21699210)吗?同样,“以下”是一个误导性术语,因为用户可以按不同字段进行排序,随着时间的推移投票也可以更改顺序。 (2认同)

Ali*_*iba 180

要保留换行符,请使用|例如:

|
  This is a very long sentence
  that spans several lines in the YAML
  but which will be rendered as a string
  with newlines preserved.
Run Code Online (Sandbox Code Playgroud)

被翻译为"这是一个非常长的句子\n,它跨越YAML \n中的几行,但它将呈现为字符串\n,并保留换行符.\n "


Ara*_*ngh 75

1.块表示法: 删除块后,换行符将成为空格和额外的换行符

---
# Note: It has 1 new line after the string
content:
    Arbitrary free text
    over multiple lines stopping
    after indentation changes...

...
Run Code Online (Sandbox Code Playgroud)

等效的JSON

{
 "content": "Arbitrary free text over multiple lines stopping after indentation changes..."
}
Run Code Online (Sandbox Code Playgroud)

2. Literal Block Scalar: 一个文字块标量| 将包括换行符和任何尾随空格.但删除额外的

块之后的换行符.

---
# After string we have 2 spaces and 2 new lines
content1: |
 Arbitrary free text
 over "multiple lines" stopping
 after indentation changes...  


...
Run Code Online (Sandbox Code Playgroud)

等效的JSON

{
 "content1": "Arbitrary free text\nover \"multiple lines\" stopping\nafter indentation changes...  \n"
}
Run Code Online (Sandbox Code Playgroud)

3. + Literal Block Scalar指标:阻止后保留额外的换行符

---
# After string we have 2 new lines
plain: |+
 This unquoted scalar
 spans many lines.


...
Run Code Online (Sandbox Code Playgroud)

等效的JSON

{
 "plain": "This unquoted scalar\nspans many lines.\n\n\n"
}
Run Code Online (Sandbox Code Playgroud)

4. - 具有Literal Block Scalar的指示符: -表示删除字符串末尾的换行符.

---
# After string we have 2 new lines
plain: |-
 This unquoted scalar
 spans many lines.


...
Run Code Online (Sandbox Code Playgroud)

等效的JSON

{
 "plain": "This unquoted scalar\nspans many lines."
}
Run Code Online (Sandbox Code Playgroud)

5.折叠块标量(>):

将换行符折叠到空格,但删除块后的额外换行符.

---
folded_newlines: >
 this is really a
 single line of text
 despite appearances


...
Run Code Online (Sandbox Code Playgroud)

等效的JSON

{
 "fold_newlines": "this is really a single line of text despite appearances\n"
}
Run Code Online (Sandbox Code Playgroud)

您可以访问我的博客


Moh*_*sen 42

您可能不相信,但YAML也可以执行多行键:

?
 >
 multi
 line
 key
:
  value
Run Code Online (Sandbox Code Playgroud)

  • 这个真实用例的任何例子都是? (4认同)
  • @ilyaigpetrov `?` 是关键指标(如映射中的键)。在许多情况下,当键后面的(必需的)值指示符 `:` 使解析没有歧义时,您可能会忽略键指示符。但事实并非如此,您必须使用它来明确标记密钥。 (4认同)
  • 需要说明(什么是"?"). (3认同)

phs*_*phs 38

要连接没有空格的长行,请使用双引号并使用反斜杠转义换行符:

key: "Loremipsumdolorsitamet,consecteturadipiscingelit,seddoeiusmodtemp\
  orincididuntutlaboreetdoloremagnaaliqua."
Run Code Online (Sandbox Code Playgroud)

(谢谢@Tobia)


Rva*_*aak 16

如果您在Symfony中使用yml和Twig进行翻译,并希望在Javascript中使用多行翻译,则会在翻译后立即添加回车符.所以即使是以下代码:

var javascriptVariable = "{{- 'key'|trans -}}";

其中有以下yml翻译:

key: >
    This is a
    multi line 
    translation.
Run Code Online (Sandbox Code Playgroud)

仍然会在html中产生以下代码:

var javascriptVariable = "This is a multi line translation.
";
Run Code Online (Sandbox Code Playgroud)

所以,Twig的减号并没有解决这个问题.解决方案是在大于登录yml之后添加此减号:

key: >-
    This is a
    multi line 
    translation.
Run Code Online (Sandbox Code Playgroud)

将在Twig的一行中获得正确的结果,多行翻译:

var javascriptVariable = "This is a multi line translation.";
Run Code Online (Sandbox Code Playgroud)


Joe*_*Joe 8

对于字符串可能包含空格或不包含空格的情况,我更喜欢双引号和带反斜杠的行继续:

key: "String \
  with long c\
  ontent"
Run Code Online (Sandbox Code Playgroud)

但请注意延续线以空格开始的情况下的缺陷,需要进行转义(因为它会在其他地方被剥离):

key: "String\
  \ with lon\
  g content"
Run Code Online (Sandbox Code Playgroud)

如果字符串包含换行符,则需要以C样式编写\n.

另见这个问题.