有趣的 Kotlin 0x02:Indent trimming

1,853 阅读1分钟

这是我参与更文挑战的第 30 天,活动详情查看: 更文挑战

最近在 portal.kotlin-academy.com/#/ 上看到很多关于 Kotlin 的有趣的题目。个人觉得很适合 Kotlin 爱好者,感兴趣的小伙伴可自行查阅。 【有趣的 Kotlin 】系列记录自己对每一题的理解。

0x02:Indent trimming

fun main(args: Array<String>) {
	val world = "multiline world"
	println("""
    	Hello
    	\$world
	""".trimIndent())
}

以上代码,运行结果是什么?可选项:

  1. Hello $world
  2.    Hello    $world
  3. Hello \multiline world
  4. doesn't compile

思考一下,记录下你心中的答案。

分析

  1. Kotlin 中的 Raw String 是用 """ 三个双引号包裹的;
  2. Kotlin 中的 Raw String 包含非转义字符、新行符,以及其它任意字符。也就是说,题中的 \ 转义字符会被当成普通字符处理;
  3. $ 符号表示处理字符串模板表达式;
  4. trimIndent() 会检测所有输入行的通用最小缩进,将其从每一行中删除。

经过上述分析,题目转义字符失效,字符串模板替换 world 变量,再结合trimIndent 函数去掉缩进,答案很明显为 选项3: Hello \multiline world

总结

转义字符串

Kotlin 中我们常用的字符串基本都是用 " 单个双引号包裹的转移字符串。 支持转义字符,也支持字符串模板表达式 ,表达式运行结果拼接至字符串内表达式所在位置。 例如:

val love = "OpenCV \nor Android"
println("I Love $love")
println("I Love \$love")

运行结果就是:

I Love OpenCV 
or Android
I Love $love

原始字符串

Kotlin 中被 """ 三个双引号包裹的内容为原始字符串(Raw String),不支持转义字符,支持字符串模板表达式。 例如:

val love = "OpenCV \nor Android"
println("""I Love $love""")
println("""I Love \$love""")

运行结果如下:

I Love OpenCV 
or Android
I Love \OpenCV 
or Android

在看看 trim()trimIndent()trimMargin()

val spaceTrim = """
    Yes
        No
    Other
""".trim()
println(spaceTrim)

val spaceTrimMargin = """
    Yes
        No
    Other
""".trimMargin()
println(spaceTrimMargin)

val spaceTrimIndent = """
    Yes
        No
    Other
""".trimIndent()
println(spaceTrimIndent)

运行结果如下: trim、trimMargin、trimIndenttrimMargin() 拿出来单独看看,源码如下:

public fun String.trimMargin(marginPrefix: String = "|"): String =
    replaceIndentByMargin("", marginPrefix)

参数 marginPrefix 默认参数为|。将其作为边界字符,方便原始字符串整理对齐。具体看下面几个例子:

val marginOne = """
    |Yes
        |No
    |Other
""".trimMargin()
println(marginOne)

val marginTwo = """
    >Yes
        >No
    >Other
""".trimMargin()
println(marginTwo)

val marginThree = """
    >Yes
        >No
    >Other
""".trimMargin(">")
println(marginThree)

运行结果如下:

Yes
No
Other
        >Yes
            >No
        >Other
Yes
No
Other