在Kotlin中,如何将InputStream的全部内容读入字符串?

我最近看到了将InputStream全部内容读入Kotlin中的字符串的代码,比如:

 // input is of type InputStream val baos = ByteArrayOutputStream() input.use { it.copyTo(baos) } val inputAsString = baos.toString() 

并且:

 val reader = BufferedReader(InputStreamReader(input)) try { val results = StringBuilder() while (true) { val line = reader.readLine() if (line == null) break results.append(line) } val inputAsString = results.toString() } finally { reader.close() } 

而且,即使这样看起来更平滑,因为它会自动关闭InputStream

 val inputString = BufferedReader(InputStreamReader(input)).useLines { lines -> val results = StringBuilder() lines.forEach { results.append(it) } results.toString() } 

或者那个稍微变化:

 val results = StringBuilder() BufferedReader(InputStreamReader(input)).forEachLine { results.append(it) } val resultsAsString = results.toString() 

然后这个功能折叠thingy:

 val inputString = input.bufferedReader().useLines { lines -> lines.fold(StringBuilder()) { buff, line -> buff.append(line) }.toString() } 

或者不能关闭InputStream错误变化:

 val inputString = BufferedReader(InputStreamReader(input)) .lineSequence() .fold(StringBuilder()) { buff, line -> buff.append(line) } .toString() 

但他们都笨重,我一直在寻找更新,不同版本的相同…其中一些甚至从来没有关闭InputStream 。 什么是非笨重(惯用)的方式来读取InputStream

注意: 这个问题是由作者故意写的和回答的( 自我回答的问题 ),所以对于常见的Kotlin话题的习惯性的回答是在SO中。

Kotlin只是为了这个目的有一个特定的扩展。

最简单的:

 val inputAsString = input.bufferedReader().use { it.readText() } // defaults to UTF-8 

在这个例子中,你可以在bufferedReader()或者reader()之间做出选择。 对函数Closeable.use()的调用将在lambda执行结束时自动关闭输入。

进一步阅读:

如果你经常做这种事情,你可以把它写成一个扩展函数:

 fun InputStream.readTextAndClose(charset: Charset = Charsets.UTF_8): String { return this.bufferedReader(charset).use { it.readText() } } 

你可以很容易地打电话给:

 val inputAsString = input.readTextAndClose() // defaults to UTF-8 

请注意,所有需要知道charset Kotlin扩展函数已经默认为UTF-8 ,所以如果你需要不同的编码,你需要调整上面的代码来调用reader(charset)或者bufferedReader(charset)

警告:您可能会看到较短的示例:

 val inputAsString = input.reader().readText() 

但是这些不关闭流 。 确保你检查了所有你使用的IO函数的API文档,以确定哪些关闭,哪些不关闭。 通常如果他们包括词use (比如useLines()或者use() ),那么你关闭流之后。 File.readText()File.readText()不同之处在于前者不保留任何开放,后者确实需要明确的关闭。

另请参阅: Kotlin IO相关的扩展功能

将InputStream的内容读取到String的示例

 import java.io.File import java.io.InputStream import java.nio.charset.Charset fun main(args: Array<String>) { val file = File("input"+File.separator+"contents.txt") var ins:InputStream = file.inputStream() var content = ins.readBytes().toString(Charset.defaultCharset()) println(content) } 

参考 – Kotlin读取文件