<html><head><meta http-equiv="Content-Type" content="text/html charset=utf-8"></head><body style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space;" class="">Oops, my apologies for misspelling your name. &nbsp;It was a typo.<div class=""><br class=""><div><blockquote type="cite" class=""><div class="">On Apr 13, 2017, at 8:35 AM, Ricardo Parada via swift-evolution &lt;<a href="mailto:swift-evolution@swift.org" class="">swift-evolution@swift.org</a>&gt; wrote:</div><br class="Apple-interchange-newline"><div class=""><div dir="auto" class="" style="font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif; font-size: 14px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; text-align: start; text-indent: 0px; text-transform: none; white-space: normal; word-spacing: 0px; -webkit-text-stroke-width: 0px; background-color: rgb(254, 254, 254);"><div class=""><span class=""></span></div><div class=""><div class="">Adriam</div><div class=""><br class=""></div><div class="">Take a look at Brent's revised proposal.I personally thin it is perfect. &nbsp;Take a look:</div><div class=""><br class=""></div><div class=""><a href="https://github.com/johnno1962a/swift-evolution/blob/master/proposals/0168-multi-line-string-literals.md" class="" style="color: rgb(65, 131, 196); background-color: inherit; text-decoration: none;">https://github.com/johnno1962a/swift-evolution/blob/master/proposals/0168-multi-line-string-literals.md</a></div><div class=""><br class=""></div><div class=""><br class=""></div><div class="">Regarding what you are proposing:</div><div class=""><b class=""><br class=""></b></div><div class=""><b class="">Trailing newline&nbsp;</b></div><div class=""><br class=""></div><div class="">We need consensus on whether the trailing newline on the last line should be included. &nbsp;You are proposing it should not be included which will add an empty line to Brent's xml concatenation example. The example looks better when the trailing newline is included.&nbsp;</div><div class=""><br class=""></div><div class="">In the more rare<span class="" style="background-color: rgba(255, 255, 255, 0);">&nbsp;</span>case where the newline is not desired on the last line then you can just include the backslash at the end. See Brent's revised proposal:&nbsp;<a href="https://github.com/johnno1962a/swift-evolution/blob/master/proposals/0168-multi-line-string-literals.md" class="" style="color: rgb(65, 131, 196); background-color: inherit; text-decoration: none;">https://github.com/johnno1962a/swift-evolution/blob/master/proposals/0168-multi-line-string-literals.md</a></div><div class=""><br class=""></div><div class=""><b class="">Trailing whitespace</b>&nbsp;</div><div class=""><br class=""></div><div class="">You also propose to remove trailing white space in each line unless the whitespace is followed by a backslash. &nbsp; For example:</div><div class=""><pre class="" style="margin: 15px 0px; font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); border: 1px solid rgb(204, 204, 204); overflow: auto; padding: 4px 8px; word-break: normal; word-wrap: normal;"><code class="swift" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 0px; margin: 0px; padding: 0px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">let str_2 = """↵  
foo··↵
"""</code></pre></div><div class="">The two trailing whitespaces after foo would get removed according to what you are proposing. I don't like this rule. I think we are better off with leaving it alone and to the tools as Brent suggested.&nbsp;</div><div class=""><br class=""></div><div class="">Regards,</div><div class="">Ricardo Parada</div><div class=""><br class=""></div><div class=""><br class=""></div><div class=""><br class=""></div><div class=""><div class=""><div class="" style="font-family: Helvetica; font-size: 14px;"><span class="" style="font-family: Menlo; font-size: 11px;"><br class=""></span></div></div>On Apr 13, 2017, at 5:28 AM, Adrian Zubarev via swift-evolution &lt;<a href="mailto:swift-evolution@swift.org" class="" style="color: rgb(65, 131, 196); background-color: inherit; text-decoration: none;">swift-evolution@swift.org</a>&gt; wrote:<br class=""><br class=""></div><blockquote type="cite" class="" style="margin: 15px 0px;"><div class="" style="margin-top: 0px; margin-bottom: 0px;"><div class="bloop_markdown"><p class="" style="margin: 15px 0px; -webkit-margin-before: 0px;">Now that I had some sleep I actually revise my opinion about the last line. I took a few hours to sum my thoughts together in a gist, here is a formatted version of it:<span class="Apple-converted-space">&nbsp;</span><a href="https://gist.github.com/DevAndArtist/dae76d4e3d4e49b1fab22ef7e86a87a9" class="" style="color: rgb(65, 131, 196); background-color: inherit; text-decoration: none; -webkit-margin-before: 0px;">https://gist.github.com/DevAndArtist/dae76d4e3d4e49b1fab22ef7e86a87a9</a></p><hr class="" style="height: 0.2em; border: 0px; color: rgb(204, 204, 204); background-color: rgb(204, 204, 204); display: inherit;"><h3 id="simplemulti-linestringliteralmodel" class="" style="font-weight: bold; font-size: 18px;">Simple ‘multi-line string literal’ model</h3><h4 id="corefeatures:" class="" style="font-weight: bold; font-size: 16px;">Core features:</h4><ol class="" style="margin: 15px 0px;"><li class="" style="margin: 15px 0px; -webkit-margin-before: 0px;">Omitting of (most) backslashes for<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">"</code>.</li><li class="" style="margin: 15px 0px;">Altering the string with implicit new line injection at the end of the line.</li></ol><h4 id="consequencesof1:" class="" style="font-weight: bold; font-size: 16px;">Consequences of #1:</h4><ul class="" style="margin: 15px 0px;"><li class="" style="margin: 15px 0px; -webkit-margin-before: 0px;"><p class="" style="margin: 15px 0px; -webkit-margin-before: 0px;">To omit escaping the quote character, the delimiter characters for the<span class="Apple-converted-space">&nbsp;</span><strong class="" style="-webkit-margin-before: 0px;">multi-line string literal</strong><span class="Apple-converted-space">&nbsp;</span>will be<span class="Apple-converted-space">&nbsp;</span><em class="">tripled quotes</em><span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">"""</code>, also similar to other programming languages.</p></li><li class="" style="margin: 15px 0px;"><p class="" style="margin: 15px 0px; -webkit-margin-before: 0px;">When a standard string literal contains at least 5 quotes, then the usage of a<span class="Apple-converted-space">&nbsp;</span><strong class="" style="-webkit-margin-before: 0px;">multi-line string literal</strong><span class="Apple-converted-space">&nbsp;</span>will be shorter.</p></li></ul><pre class="" style="margin: 15px 0px; font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(204, 204, 204); overflow: auto; padding: 4px 8px; word-break: normal; word-wrap: normal;"><code class="swift" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 0px; margin: 0px; padding: 0px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">"&lt;a href=\"\(url)\" id=\"link\(i)\" class=\"link\"&gt;"    // With escapes
"""&lt;a href="\(url)" id="link\(i)" class="link"&gt;"""      // With tripled literals
</code></pre><h4 id="consequencesof2:" class="" style="font-weight: bold; font-size: 16px;">Consequences of #2:</h4><ul class="" style="margin: 15px 0px;"><li class="" style="margin: 15px 0px; -webkit-margin-before: 0px;"><p class="" style="margin: 15px 0px; -webkit-margin-before: 0px;">To fully support this feature, we need to compromise the design for simplicity and intuitivity.</p><ul class="" style="margin: 15px 0px;"><li class="" style="margin: 15px 0px; -webkit-margin-before: 0px;">This feature needs precision for leading and trailing spaces.</li><li class="" style="margin: 15px 0px;">Alternatively one would need a way to disable new line injection to also support code formatting.</li></ul></li></ul><h4 id="twowaysofwritingamulti-linestringliteral:" class="" style="font-weight: bold; font-size: 16px;">Two ways of writing a multi-line string literal:</h4><ul class="" style="margin: 15px 0px;"><li class="" style="margin: 15px 0px; -webkit-margin-before: 0px;"><p class="" style="margin: 15px 0px; -webkit-margin-before: 0px;">Single line version<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">"""abc"""</code><span class="Apple-converted-space">&nbsp;</span>is trivial and already was shown above.</p></li><li class="" style="margin: 15px 0px;"><p class="" style="margin: 15px 0px; -webkit-margin-before: 0px;">The multi-line version comes with a few compromises for simplicity of rules:</p></li></ul><pre class="" style="margin: 15px 0px; font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(204, 204, 204); overflow: auto; padding: 4px 8px; word-break: normal; word-wrap: normal;"><code class="swift" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 0px; margin: 0px; padding: 0px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">"""   // DS (delimiter start)
foo   // s0
foo   // s1
foo   // s2
"""   // DE (delimiter end)
</code></pre><ul class="" style="margin: 15px 0px;"><li class="" style="margin: 15px 0px; -webkit-margin-before: 0px;"><p class="" style="margin: 15px 0px; -webkit-margin-before: 0px;">The string content is always written between the lines<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">DS</code><span class="Apple-converted-space">&nbsp;</span>and<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">DE</code><span class="Apple-converted-space">&nbsp;</span>(delimiter lines).<span class="Apple-converted-space">&nbsp;</span></p></li><li class="" style="margin: 15px 0px;"><p class="" style="margin: 15px 0px; -webkit-margin-before: 0px;">To not to go the<span class="Apple-converted-space">&nbsp;</span><strong class="" style="-webkit-margin-before: 0px;">continuation quotes</strong><span class="Apple-converted-space">&nbsp;</span>path, the left (or leading) precision is handled by the<span class="Apple-converted-space">&nbsp;</span><em class="">closing delimiter</em><span class="Apple-converted-space">&nbsp;</span>(<strong class="">1. compromise</strong>). The closing delimiter is also responsible for the indent algorithm, which will calculate the stripping prefix in line<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">DE</code><span class="Apple-converted-space">&nbsp;</span>and apply stripping to lines<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">s0</code><span class="Apple-converted-space">&nbsp;</span>to<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">sn</code>.</p></li><li class="" style="margin: 15px 0px;"><p class="" style="margin: 15px 0px; -webkit-margin-before: 0px;">Right (or trailing) precision of each line from<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">s0</code><span class="Apple-converted-space">&nbsp;</span>to<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">sn</code><span class="Apple-converted-space">&nbsp;</span>(notice n equals 2 in the example above) is handled by a backslash character (<strong class="">2. compromise</strong>).</p></li><li class="" style="margin: 15px 0px;"><p class="" style="margin: 15px 0px; -webkit-margin-before: 0px;">The right precision comes at a price of losing the implicit new line injection, however this was also a requested feature (<strong class="" style="-webkit-margin-before: 0px;">3. compromise</strong>). That means that the backslash serves two jobs simultaneously.</p></li><li class="" style="margin: 15px 0px;"><p class="" style="margin: 15px 0px; -webkit-margin-before: 0px;">New line injection happens only on lines<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">s0</code><span class="Apple-converted-space">&nbsp;</span>to<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">s(n - 1)</code><span class="Apple-converted-space">&nbsp;</span>(<strong class="">4. and last compromise</strong><span class="Apple-converted-space">&nbsp;</span>of the design). The last line<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">sn</code><span class="Apple-converted-space">&nbsp;</span>(or<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">s2</code><span class="Apple-converted-space">&nbsp;</span>above) does not inject a new line into the final string. This implies that in this line a backslash character handles only right precision, or one could say it’s reduced to one functionality.</p></li></ul><hr class="" style="height: 0.2em; border: 0px; color: rgb(204, 204, 204); background-color: rgb(204, 204, 204); display: inherit;"><h4 id="important:" class="" style="font-weight: bold; font-size: 16px;">Important:</h4><p class="" style="margin: 15px 0px;">Because whitespace is important to these examples, it is explicitly indicated:<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">·</code><span class="Apple-converted-space">&nbsp;</span>is a space,<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">⇥</code><span class="Apple-converted-space">&nbsp;</span>is a tab, and<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">↵</code><span class="Apple-converted-space">&nbsp;</span>is a newline.</p><h5 id="leadingtrailingprecisionandindent1.and2.compromise:" class="" style="font-weight: bold; font-size: 14px;">Leading/trailing precision and indent (1. and 2. compromise):</h5><pre class="" style="margin: 15px 0px; font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(204, 204, 204); overflow: auto; padding: 4px 8px; word-break: normal; word-wrap: normal;"><code class="swift" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 0px; margin: 0px; padding: 0px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">// Nothing to strip in this example (no ident).
let str_1 = """↵  
foo↵
"""

// No right precision (no backslash) -&gt; whitespaces will be stripped.
let str_2 = """↵  
foo··↵
"""

// Same as `str_2`
let str_3 = """↵  
foo····↵
"""

// Line `DE` of the closing delimiter calculates the indent prefix  
// `··` and strips it from `s0` (left precision).
let str_4 = """↵  
··foo↵
··"""

// Line `DE` of the closing delimiter calculates the indent prefix  
// `····` and strips it from `s0` (left precision).
// No right precision (no backslash) -&gt; whitespaces will be stripped.
let str_5 = """↵  
····foo··↵
····"""

// Line `DE` of the closing delimiter calculates the indent prefix  
// `⇥ ⇥ ` and strips it from `s0` (left precision).
// Right precision is applied (backslash). In this case the literal
// contains only a single line of content, which happens to be   
// also the last line before `DE` -&gt; backslash only serves precision.
let str_6 = """↵  
⇥ ⇥ foo\↵
⇥ ⇥ """

// Line `DE` of the closing delimiter calculates the indent prefix  
// `·⇥ ·⇥ ` and strips it from `s0` (left precision).
// No right precision (no backslash) -&gt; whitespaces will be stripped.
let str_7 = """↵  
·⇥ ·⇥ foo··↵
·⇥ ·⇥ """

let string_1 = "foo"

str_1 == string_1   // =&gt; true
str_2 == string_1   // =&gt; true
str_3 == string_1   // =&gt; true
str_4 == string_1   // =&gt; true
str_5 == string_1   // =&gt; true
str_6 == string_1   // =&gt; true
str_7 == string_1   // =&gt; true
</code></pre><p class="" style="margin: 15px 0px;">A false multi-line string literal, which compiles but emits a warning and proves a<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">fix-it</code>:</p><pre class="" style="margin: 15px 0px; font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(204, 204, 204); overflow: auto; padding: 4px 8px; word-break: normal; word-wrap: normal;"><code class="swift" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 0px; margin: 0px; padding: 0px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">let str_8 = """↵  
··foo↵
····"""

str_8 == string_1   // =&gt; true
</code></pre><pre class="" style="margin: 15px 0px; font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(204, 204, 204); overflow: auto; padding: 4px 8px; word-break: normal; word-wrap: normal;"><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 0px; margin: 0px; padding: 0px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">warning: missing indentation in multi-line string literal
  ··foo!
    ^  
  Fix-it: Insert "··"
</code></pre><ul class="" style="margin: 15px 0px;"><li class="" style="margin: 15px 0px; -webkit-margin-before: 0px;"><p class="" style="margin: 15px 0px; -webkit-margin-before: 0px;">The stripping algorithm calculates the prefix indent from the closing delimiter line<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">DE</code><span class="Apple-converted-space">&nbsp;</span>and tries to strip it in lines<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">s0</code><span class="Apple-converted-space">&nbsp;</span>to<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">sn</code><span class="Apple-converted-space">&nbsp;</span>if possible, otherwise each line, which could not be handled correctly will emit an individual warning and a<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">fix-it</code>.</p></li><li class="" style="margin: 15px 0px;"><p class="" style="margin: 15px 0px; -webkit-margin-before: 0px;">The stripping algorithm removes every whitespace on the end of each line from<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">s0</code><span class="Apple-converted-space">&nbsp;</span>to<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">sn</code><span class="Apple-converted-space">&nbsp;</span>iff there is no right precision, annotated through a backslash like<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">··foo··\↵</code>. This behavior is essential and aligns well with the precision behavior of a standard string literal<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">" "</code>, otherwise a<span class="Apple-converted-space">&nbsp;</span><strong class="">multi-line string literal</strong><span class="Apple-converted-space">&nbsp;</span>like</p></li></ul><pre class="" style="margin: 15px 0px; font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(204, 204, 204); overflow: auto; padding: 4px 8px; word-break: normal; word-wrap: normal;"><code class="swift" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 0px; margin: 0px; padding: 0px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">"""
foo
"""
</code></pre><p class="" style="margin: 15px 0px;">can contain 3 characters or 10 characters or even 1000 characters, but the developer couldn’t tell or even approximately guess.</p><p class="" style="margin: 15px 0px;">The correct way of fixing this, as already mentioned above, is by striping all white spaces after the last non-space character of the line, unless the right precision is explicitly annotated with a backslash.</p><pre class="" style="margin: 15px 0px; font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(204, 204, 204); overflow: auto; padding: 4px 8px; word-break: normal; word-wrap: normal;"><code class="swift" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 0px; margin: 0px; padding: 0px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">"""
foo   \
"""
</code></pre><h5 id="disablingnewlineinjection3.compromise:" class="" style="font-weight: bold; font-size: 14px;">Disabling new line injection (3. compromise):</h5><p class="" style="margin: 15px 0px;">The examples we’ve used so far had only a single content line, so we couldn’t showcase the behavior yet. New lines are only injected into a multi-line string if it has at least two content lines.</p><pre class="" style="margin: 15px 0px; font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(204, 204, 204); overflow: auto; padding: 4px 8px; word-break: normal; word-wrap: normal;"><code class="swift" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 0px; margin: 0px; padding: 0px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">let str_9 = """↵  
····foo↵
····bar↵
····"""

let str_10 = """↵  
····foo↵
····bar↵
····baz↵
····"""

let string_2 = "foo\nbar"
let string_3 = "foor\nbar\nbaz"

str_9 == string_2  // =&gt; true
str_10 == string_3 // =&gt; true
</code></pre><p class="" style="margin: 15px 0px;">To disable new line injection one would need to use the backslash for right precision.</p><pre class="" style="margin: 15px 0px; font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(204, 204, 204); overflow: auto; padding: 4px 8px; word-break: normal; word-wrap: normal;"><code class="swift" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 0px; margin: 0px; padding: 0px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">let str_11 = """↵  
····foo\↵
····bar↵
····"""

let str_12 = """↵  
····foo\↵
····bar\↵
····baz↵
····"""

str_11 == string_2    // =&gt; false
str_12 == string_3    // =&gt; false

str_11 == "foorbar"   // =&gt; true
str_12 == "foobarbaz" // =&gt; true
</code></pre><p class="" style="margin: 15px 0px;">Remember that the last content line<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">sn</code><span class="Apple-converted-space">&nbsp;</span>does not automatically inject a new line into the final string!</p><h5 id="newlineinjectionexceptforthelastline4.compromise:" class="" style="font-weight: bold; font-size: 14px;">New line injection except for the last line (4. compromise):</h5><p class="" style="margin: 15px 0px;">The standard string literal like<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">"foo"</code><span class="Apple-converted-space">&nbsp;</span>only contains its string content from the starting delimiter to the closing delimiter. The discussion on the mailing list suggests that the<span class="Apple-converted-space">&nbsp;</span><strong class="">multi-line string literal</strong><span class="Apple-converted-space">&nbsp;</span>should also go that route and not inject a new line for the last content line<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">sn</code>.<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal;">str_9</code><span class="Apple-converted-space">&nbsp;</span>is a good example for that behavior.<span class="Apple-converted-space">&nbsp;</span></p><p class="" style="margin: 15px 0px;">Now if one would want a new line at the end of the string, there are a few options to achieve this:</p><pre class="" style="margin: 15px 0px; font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(204, 204, 204); overflow: auto; padding: 4px 8px; word-break: normal; word-wrap: normal;"><code class="swift" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 0px; margin: 0px; padding: 0px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">// Natural way:
let str_13 = """↵  
····foo↵
····bar↵
····↵
····"""

// Remember the last content line does not inject a `\n` character by default
// so there is no need for `\n\` here (but it's possible as well)!
let str_14 = """↵  
····foo↵
····bar\n↵
····"""

str_13 == "foo\nbar\n" // =&gt; true
</code></pre><p class="" style="margin: 15px 0px;">At first glance the behavior in<span class="Apple-converted-space">&nbsp;</span><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(234, 234, 234); margin: 0px 2px; padding: 0px 5px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">str_13</code><span class="Apple-converted-space">&nbsp;</span>seems odd and inconsistent, however it actually mimics perfectly the natural way of writing text paragraphs.</p><pre class="" style="margin: 15px 0px; font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(204, 204, 204); overflow: auto; padding: 4px 8px; word-break: normal; word-wrap: normal;"><code class="" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 0px; margin: 0px; padding: 0px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">[here is a blank line]↵
text text text tex text↵
text text text tex text↵
[here is a blank line]
</code></pre><p class="" style="margin: 15px 0px;">This is easily expressed with the literal model expressed above:</p><pre class="" style="margin: 15px 0px; font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 1px solid rgb(204, 204, 204); overflow: auto; padding: 4px 8px; word-break: normal; word-wrap: normal;"><code class="swift" style="font-family: Menlo, Consolas, 'Liberation Mono', Courier, monospace; font-size: 10pt; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; background-color: rgb(248, 248, 248); color: inherit; border: 0px; margin: 0px; padding: 0px; word-break: normal; word-wrap: normal; -webkit-margin-before: 0px;">let myParagraph = """↵
····↵
····text text text tex text↵
····text text text tex text↵
····↵
····"""
</code></pre><div class=""><br class="webkit-block-placeholder" style="-webkit-margin-before: 0px;"></div></div><div class="bloop_original_html"><div id="bloop_customfont" class="" style="font-family: Helvetica, Arial; font-size: 13px; margin: 0px;"><br class=""></div><br class=""><div id="bloop_sign_1492075149230121216" class="bloop_sign"><div class="" style="font-family: helvetica, arial; font-size: 13px;">--&nbsp;<br class="">Adrian Zubarev<br class="">Sent with Airmail</div></div><br class=""><p class="airmail_on" style="margin: 15px 0px;">Am 13. April 2017 um 02:39:51, Xiaodi Wu (<a href="mailto:xiaodi.wu@gmail.com" class="" style="color: rgb(65, 131, 196); background-color: inherit; text-decoration: none;">xiaodi.wu@gmail.com</a>) schrieb:</p><blockquote type="cite" class="clean_bq" style="margin: 15px 0px;"><span class="" style="margin-top: 0px; margin-bottom: 0px;"><div class=""><div class=""></div><div class=""><div dir="ltr" class="">On Wed, Apr 12, 2017 at 5:20 PM, Brent Royal-Gordon<span class="Apple-converted-space">&nbsp;</span><span dir="ltr" class="">&lt;<a href="mailto:brent@architechies.com" target="_blank" class="" style="color: rgb(65, 131, 196); background-color: inherit; text-decoration: none;">brent@architechies.com</a>&gt;</span><span class="Apple-converted-space">&nbsp;</span>wrote:<br class=""><div class="gmail_extra"><div class="gmail_quote"><blockquote class="gmail_quote" style="margin: 0px 0px 0px 0.8ex; border-left-width: 1px; border-left-style: solid; border-left-color: rgb(204, 204, 204); padding-left: 1ex;"><div class="" style="margin-top: 0px; margin-bottom: 0px; word-wrap: break-word;"><div class="">Wow, maybe I shouldn't have slept.</div><div class=""><br class=""></div><div class="">Okay, let's deal with trailing newline first. I'm *very* confident that trailing newlines should be kept by default. This opinion comes from lots of practical experience with multiline string features in other languages. In practice, if you're generating files in a line-oriented way, you're usually generating them a line at a time. It's pretty rare that you want to generate half a line and then add more to it in another statement; it's more likely you'll interpolate the data. I'm not saying it doesn't happen, of course, but it happens a lot less often than you would think just sitting by the fire, drinking whiskey and musing over strings.</div><div class=""><br class=""></div><div class="">I know that, if you're pushing for this feature, it's not satisfying to have the answer be "trust me, it's not what you want". But trust me, it's not what you want.</div></div></blockquote><div class=""><br class=""></div><div class="">This is not a very good argument. If you are generating files in a line-oriented way, it is the function _emitting_ the string that handles the line-orientedness, not the string itself. That is the example set by `print()`:</div><div class=""><br class=""></div><div class="">```</div><div class="">print("Hello, world!") // Emits "Hello, world!\n"</div><div class="">```</div><div class=""><br class=""></div><div class="">Once upon a time, if I recall, this function was called `println`, but it was renamed. This particular example demonstrates why keeping trailing newlines by default is misguided:</div><div class=""><br class=""></div><div class="">```</div><div class="">print(</div><div class="">&nbsp; """</div><div class="">&nbsp; Hello, world!</div><div class="">&nbsp; """</div><div class="">)</div><div class="">```</div><div class=""><br class=""></div><div class="">Under your proposed rules, this emits "Hello, world!\n\n". It is almost certainly not what you want. Instead, it is a misguided attempt by the designers of multiline string syntax to do the job that the designers of `print()` have already accounted for.</div><div class=""><br class=""></div><div class="">If we were to buy your line of reasoning and adapt it for single-line strings, we would arrive at a rather absurd result. If you're emitting multiple single-line strings, you almost certainly want a space to separate them. Again this is exemplified by the behavior of `print()`:</div><div class=""><br class=""></div><div class="">```</div><div class="">print("Hello", "Brent!")</div><div class="">```</div><div class=""><br class=""></div><div class="">This emits "Hello Brent!" (and not "HelloBrent!"). But we do not take that reasoning and demand that "This is my string" end with an default trailing space, nor do we have `+` concatenate strings by default with a separating space.</div><div class=""><br class=""></div><div class=""><br class=""></div><blockquote class="gmail_quote" style="margin: 0px 0px 0px 0.8ex; border-left-width: 1px; border-left-style: solid; border-left-color: rgb(204, 204, 204); padding-left: 1ex;"><div class="" style="margin-top: 0px; margin-bottom: 0px; word-wrap: break-word;"><div class="">Moving to the other end, I think we could do a leading newline strip *if* we're willing to create multiline and non-multiline modes—that is, newlines are _not allowed at all_ unless the opening delimiter ends its line and the closing delimiter starts its line (modulo indentation). But I'm reluctant to do that because, well, it's weird and complicated. I also get the feeling that, if there's a single-line mode and a multi-line mode, we ought to treat them as truly orthogonal features and allow `"`-delimited strings to use multi-line mode, but I'm really not convinced that's a good idea.</div><div class=""><br class=""></div><div class="">(Note, by the way, that heredocs—a *really* common multiline string design—always strip the leading newline but not the trailing one.)</div><div class=""><br class=""></div><div class="">Adrian cited this example, where I agree that you really don't want the string to be on the same line as the leading delimiter:</div><div class=""><br class=""></div><div class=""><div class="">let myReallyLongXMLConstantName = """&lt;?xml version="1.0"?&gt;</div><div class="">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&lt;catalog&gt;</div><div class="">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &lt;book id="bk101" empty=""&gt;</div><div class="">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&lt;author&gt;John Doe&lt;/author&gt;</div><div class="">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&lt;title&gt;XML Developer's Guide&lt;/title&gt;</div><div class="">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&lt;genre&gt;Computer&lt;/genre&gt;</div><div class="">&nbsp; &nbsp; &nbsp; &nbsp;&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&lt;price&gt;44.95&lt;/price&gt;</div><div class="">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &lt;/book&gt;</div><div class="">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&lt;/catalog&gt;\</div><div class="">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;""" &nbsp; &nbsp; &nbsp; &nbsp;</div><br class="gmail-m_-4413069624854317166Apple-interchange-newline">But there are lots of places where it works fine. Is there a good reason to force an additional newline in this?</div><div class=""><br class=""></div><div class=""><div class="">case .isExprSameType(let from, let to):</div></div><div class=""><div class="">return """checking a value with optional type \(from) against dynamic type \(to) \</div><div class="">&nbsp; &nbsp; &nbsp;&nbsp;succeeds whenever the value is non-'nil'; did you mean to use '!= nil'?\</div><div class="">&nbsp; &nbsp; &nbsp;&nbsp;"""</div></div><div class=""><br class=""></div><div class="">I mean, we certainly could, but I'm not convinced we should. At least, not yet.</div><div class=""><br class=""></div><div class="">In any case, trailing newline definitely stays. Leading newline, I'm still thinking about.</div><div class=""><br class=""></div><div class="">As for other things:</div><div class=""><br class=""></div><div class="">* I see zero reason to fiddle with trailing whitespace. If it's there, it might be significant or it might not be. If we strip it by default and we shouldn't, the developer has no way to protect it. Let's trust the developer. (And their tooling—Xcode, I believe Git, and most linters already have trailing whitespace features. We don't need them too.)</div><div class=""><br class=""></div><div class="">* Somebody asked about `"""`-delimited heredocs. I think it's a pretty syntax, but it's not compatible with single-line use of `"""`, and I think that's probably more important. We can always add heredocs in another way if we decide we want them. (I think `#to(END)` is another very Swifty syntax we could use for heredocs--less lightweight, but it gives us a Google-able keyword.)</div><div class=""><br class=""></div><div class="">* Literal spaces and tabs cannot be backslashed. This is really important because, if you see a backslash after the last visible character in a line, you can't tell just by looking whether the next character is a space, tab, or newline. So the solution is, if it's not a newline, it's not valid at all.</div><div class=""><br class=""></div><div class="">I'll respond to Jarod separately.</div><br class=""><div class=""><blockquote type="cite" class="" style="margin: 15px 0px;"><div class="" style="margin-top: 0px;">On Apr 12, 2017, at 12:07 PM, John Holdsworth &lt;<a href="mailto:mac@johnholdsworth.com" target="_blank" class="" style="color: rgb(65, 131, 196); background-color: inherit; text-decoration: none;">mac@johnholdsworth.com</a>&gt; wrote:</div><br class="gmail-m_-4413069624854317166Apple-interchange-newline"><div class="" style="margin-bottom: 0px;"><div class="" style="word-wrap: break-word;"><div class="">Finally.. a&nbsp;<a href="http://johnholdsworth.com/swift-LOCAL-2017-04-12-a-osx.tar.gz" target="_blank" class="" style="color: rgb(65, 131, 196); background-color: inherit; text-decoration: none;">new Xcode toolchain</a>&nbsp;is available largely in sync with the proposal as is.</div><div class="">(You need to restart Xcode after selecting the toolchain to restart SourceKit)</div><div class=""><br class=""></div><div class="">I personally am undecided whether to remove the first line if it is empty. The new</div><div class="">rules are more consistent but somehow less practical. A blank initial line is almost</div><div class="">never what a user would want and I would tend towards removing it automatically.</div><div class="">This is almost what a user would it expect it to do.</div><div class=""><br class=""></div><div class="">I’m less sure the same applies to the trailing newline. If this is a syntax for</div><div class="">multi-line strings, I'd argue that they should normally be complete lines -</div><div class="">particularly since the final newline can so easily be escaped.</div><div class=""><span class="gmail-"><br class=""></span></div><div class=""><span class="gmail-"><span class="" style="font-family: menlo; font-size: 11px; font-variant-ligatures: no-common-ligatures;">&nbsp; &nbsp; &nbsp; &nbsp;&nbsp;</span><span class="" style="font-family: menlo; font-size: 11px; font-variant-ligatures: no-common-ligatures; color: rgb(186, 45, 162);">let</span><span class="Apple-converted-space">&nbsp;</span><span class="" style="font-family: menlo; font-size: 11px; font-variant-ligatures: no-common-ligatures;">longstring = ""</span><span class="" style="font-family: menlo; font-size: 11px; font-variant-ligatures: no-common-ligatures; color: rgb(209, 47, 27);">"\</span></span></div><div class=""><div class="" style="margin: 0px; font-size: 11px; line-height: normal; font-family: menlo; color: rgb(209, 47, 27);"><span class="" style="font-variant-ligatures: no-common-ligatures;">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod \</span></div><div class="" style="margin: 0px; font-size: 11px; line-height: normal; font-family: menlo; color: rgb(209, 47, 27);"><span class="" style="font-variant-ligatures: no-common-ligatures;">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, \</span></div><div class="" style="margin: 0px; font-size: 11px; line-height: normal; font-family: menlo; color: rgb(209, 47, 27);"><span class="" style="font-variant-ligatures: no-common-ligatures;">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat.\</span></div><div class="" style="margin: 0px; font-size: 11px; line-height: normal; font-family: menlo; color: rgb(209, 47, 27);"><span class="" style="font-variant-ligatures: no-common-ligatures;">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; "</span><span class="" style="font-variant-ligatures: no-common-ligatures;">""</span></div><div class="" style="margin: 0px; font-size: 11px; line-height: normal; font-family: menlo; min-height: 13px;"><br class=""></div><div class="" style="margin: 0px; font-size: 11px; line-height: normal; font-family: menlo;"><span class="" style="font-variant-ligatures: no-common-ligatures;">&nbsp; &nbsp; &nbsp; &nbsp;</span><span class="Apple-converted-space">&nbsp;</span><span class="" style="font-variant-ligatures: no-common-ligatures; color: rgb(62, 30, 129);">print</span><span class="" style="font-variant-ligatures: no-common-ligatures;">( ""</span><span class="" style="font-variant-ligatures: no-common-ligatures; color: rgb(209, 47, 27);">"\</span></div><div class="" style="margin: 0px; font-size: 11px; line-height: normal; font-family: menlo; color: rgb(209, 47, 27);"><span class="" style="font-variant-ligatures: no-common-ligatures;">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; Usage: myapp &lt;options&gt;</span></div><div class="" style="margin: 0px; font-size: 11px; line-height: normal; font-family: menlo; color: rgb(209, 47, 27); min-height: 13px;"><span class="" style="font-variant-ligatures: no-common-ligatures;">&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><br class="gmail-m_-4413069624854317166webkit-block-placeholder"></div><div class="" style="margin: 0px; font-size: 11px; line-height: normal; font-family: menlo; color: rgb(209, 47, 27);"><span class="" style="font-variant-ligatures: no-common-ligatures;">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; Run myapp to do mything</span></div><div class="" style="margin: 0px; font-size: 11px; line-height: normal; font-family: menlo; color: rgb(209, 47, 27); min-height: 13px;"><span class="" style="font-variant-ligatures: no-common-ligatures;">&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;</span><br class="gmail-m_-4413069624854317166webkit-block-placeholder"></div><div class="" style="margin: 0px; font-size: 11px; line-height: normal; font-family: menlo; color: rgb(209, 47, 27);"><span class="" style="font-variant-ligatures: no-common-ligatures;">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; Options:</span></div><div class="" style="margin: 0px; font-size: 11px; line-height: normal; font-family: menlo; color: rgb(209, 47, 27);"><span class="" style="font-variant-ligatures: no-common-ligatures;">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; -myoption - an option</span></div><div class="" style="margin: 0px; font-size: 11px; line-height: normal; font-family: menlo; color: rgb(209, 47, 27);"><span class="" style="font-variant-ligatures: no-common-ligatures;">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; "</span><span class="" style="font-variant-ligatures: no-common-ligatures;">"" )</span></div></div><div class=""><span class="" style="font-variant-ligatures: no-common-ligatures;"><br class=""></span></div><div class="">(An explicit “\n" in the string should never be stripped btw)</div><div class=""><br class=""></div><div class="">Can we have a straw poll for the three alternatives:</div><div class=""><span class="gmail-"><br class=""></span></div><div class=""><span class="gmail-">1) Proposal as it stands &nbsp;- no magic removal of leading/training blank lines.</span></div><div class=""><span class="gmail-">2) Removal of a leading blank line when indent stripping is being applied.</span></div><div class=""><span class="gmail-">3) Removal of leading blank line and trailing newline when indent stripping is being applied.</span></div><div class=""><span class="gmail-"><br class=""></span></div><div class="">My vote is for the pragmatic path: 2)</div><div class=""><br class=""></div><div class="">(The main intent of this revision was actually removing the link between how the</div><div class="">string started and whether indent stripping was applied which was unnecessary.)</div><br class=""><div class=""><blockquote type="cite" class="" style="margin: 15px 0px;"><div class="" style="margin-top: 0px;">On 12 Apr 2017, at 17:48, Xiaodi Wu via swift-evolution &lt;<a href="mailto:swift-evolution@swift.org" target="_blank" class="" style="color: rgb(65, 131, 196); background-color: inherit; text-decoration: none;">swift-evolution@swift.org</a>&gt; wrote:</div><br class="gmail-m_-4413069624854317166Apple-interchange-newline"><div class="" style="margin-bottom: 0px;"><span class="" style="font-family: helvetica; font-size: 12px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; text-align: start; text-indent: 0px; text-transform: none; white-space: normal; word-spacing: 0px; float: none; display: inline;">Agree. I prefer the new rules over the old, but considering common use cases, stripping the leading and trailing newline makes for a more pleasant experience than not stripping either of them.</span><br class="" style="font-family: helvetica; font-size: 12px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; text-align: start; text-indent: 0px; text-transform: none; white-space: normal; word-spacing: 0px;"><br class="" style="font-family: helvetica; font-size: 12px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; text-align: start; text-indent: 0px; text-transform: none; white-space: normal; word-spacing: 0px;"><span class="" style="font-family: helvetica; font-size: 12px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; text-align: start; text-indent: 0px; text-transform: none; white-space: normal; word-spacing: 0px; float: none; display: inline;">I think that is generally worth prioritizing over a simpler algorithm or even accommodating more styles. Moreover, a user who wants a trailing or leading newline merely types an extra one if there is newline stripping, so no use cases are made difficult, only a very common one is made more ergonomic.</span></div></blockquote></div><br class=""></div></div></blockquote></div><span class="gmail-HOEnZb"><font color="#888888" class=""><br class=""></font></span><div class=""><div class=""><div class="" style="font-size: 12px;"><span class="gmail-HOEnZb"><font color="#888888" class="">--&nbsp;</font></span></div><div class="" style="font-size: 12px;"><span class="gmail-HOEnZb"><font color="#888888" class="">Brent Royal-Gordon</font></span></div><div class="" style="font-size: 12px;"><span class="gmail-HOEnZb"><font color="#888888" class="">Architechies</font></span></div></div></div><span class="gmail-HOEnZb"><br class=""></span></div></blockquote></div><br class=""></div></div></div></div></span></blockquote></div><div class="bloop_markdown"><div class="" style="-webkit-margin-before: 0px;"><br class="webkit-block-placeholder" style="-webkit-margin-before: 0px;"></div></div></div></blockquote><blockquote type="cite" class="" style="margin: 15px 0px;"><div class="" style="margin-top: 0px; margin-bottom: 0px;"><span class="">_______________________________________________</span><br class=""><span class="">swift-evolution mailing list</span><br class=""><span class=""><a href="mailto:swift-evolution@swift.org" class="" style="color: rgb(65, 131, 196); background-color: inherit; text-decoration: none;">swift-evolution@swift.org</a></span><br class=""><span class=""><a href="https://lists.swift.org/mailman/listinfo/swift-evolution" class="" style="color: rgb(65, 131, 196); background-color: inherit; text-decoration: none;">https://lists.swift.org/mailman/listinfo/swift-evolution</a></span><br class=""></div></blockquote></div></div><span style="font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif; font-size: 14px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; text-align: start; text-indent: 0px; text-transform: none; white-space: normal; word-spacing: 0px; -webkit-text-stroke-width: 0px; background-color: rgb(254, 254, 254); float: none; display: inline !important;" class="">_______________________________________________</span><br style="font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif; font-size: 14px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; text-align: start; text-indent: 0px; text-transform: none; white-space: normal; word-spacing: 0px; -webkit-text-stroke-width: 0px; background-color: rgb(254, 254, 254);" class=""><span style="font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif; font-size: 14px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; text-align: start; text-indent: 0px; text-transform: none; white-space: normal; word-spacing: 0px; -webkit-text-stroke-width: 0px; background-color: rgb(254, 254, 254); float: none; display: inline !important;" class="">swift-evolution mailing list</span><br style="font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif; font-size: 14px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; text-align: start; text-indent: 0px; text-transform: none; white-space: normal; word-spacing: 0px; -webkit-text-stroke-width: 0px; background-color: rgb(254, 254, 254);" class=""><a href="mailto:swift-evolution@swift.org" style="color: rgb(65, 131, 196); background-color: rgb(254, 254, 254); text-decoration: none; font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif; font-size: 14px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; orphans: auto; text-align: start; text-indent: 0px; text-transform: none; white-space: normal; widows: auto; word-spacing: 0px; -webkit-text-size-adjust: auto; -webkit-text-stroke-width: 0px;" class="">swift-evolution@swift.org</a><br style="font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif; font-size: 14px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; text-align: start; text-indent: 0px; text-transform: none; white-space: normal; word-spacing: 0px; -webkit-text-stroke-width: 0px; background-color: rgb(254, 254, 254);" class=""><a href="https://lists.swift.org/mailman/listinfo/swift-evolution" style="color: rgb(65, 131, 196); background-color: rgb(254, 254, 254); text-decoration: none; font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif; font-size: 14px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; orphans: auto; text-align: start; text-indent: 0px; text-transform: none; white-space: normal; widows: auto; word-spacing: 0px; -webkit-text-size-adjust: auto; -webkit-text-stroke-width: 0px;" class="">https://lists.swift.org/mailman/listinfo/swift-evolution</a><br style="font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif; font-size: 14px; font-style: normal; font-variant-caps: normal; font-weight: normal; letter-spacing: normal; text-align: start; text-indent: 0px; text-transform: none; white-space: normal; word-spacing: 0px; -webkit-text-stroke-width: 0px; background-color: rgb(254, 254, 254);" class=""></div></blockquote></div><br class=""></div></body></html>