如何逐行读取标准输入?
Posted
技术标签:
【中文标题】如何逐行读取标准输入?【英文标题】:How to read from standard input line by line? 【发布时间】:2011-06-02 21:47:28 【问题描述】:从标准输入逐行读取的 Scala 方法是什么?类似于等效的 java 代码:
import java.util.Scanner;
public class ScannerTest
public static void main(String args[])
Scanner sc = new Scanner(System.in);
while(sc.hasNext())
System.out.println(sc.nextLine());
【问题讨论】:
【参考方案1】:对于控制台,您可以使用Console.readLine
。你可以写(如果你想停在一个空行上):
Iterator.continually(Console.readLine).takeWhile(_.nonEmpty).foreach(line => println("read " + line))
如果您使用 cat 文件来生成输入,您可能需要使用以下命令在 null 或空时停止:
@inline def defined(line: String) =
line != null && line.nonEmpty
Iterator.continually(Console.readLine).takeWhile(defined(_)).foreach(line => println("read " + line))
【讨论】:
我知道 Console.readLine(),我正在寻找一个给定的食谱。从标准输入逐行读取的“scala”方式。 我想你的意思是takeWhile(_ != null)
取决于您要如何停止。寻找空行通常是最简单的解决方案。
请注意,从 Scala 2.11.0 开始,Console.readLine
已被弃用,请改用 StdIn.readline
。
或.takeWhile(Option(_).nonEmpty)
可能会更好,以防您想完全避免使用null
关键字。【参考方案2】:
val input = Source.fromInputStream(System.in);
val lines = input.getLines.collect
【讨论】:
io.Source.stdin
被定义(在scala.io.Source
类中)为def stdin = fromInputStream(System.in)
,所以最好坚持使用io.Source.stdin
。
这似乎不适用于 Scala 2.12.4,或者我没有找到要导入的正确内容。
它在 Scala 2.12 中工作,只是 collect
方法在这个答案中发生了变化,所以你只需要调用 input.getLines
,它会给你一个 Iterator
。您可以使用.toStream
或.toList
强制它实现,具体取决于用例。【参考方案3】:
最直接的方法就是使用readLine()
,它是Predef
的一部分。然而,这相当难看,因为您需要检查最终的 null 值:
object ScannerTest
def main(args: Array[String])
var ok = true
while (ok)
val ln = readLine()
ok = ln != null
if (ok) println(ln)
这太冗长了,你宁愿使用java.util.Scanner
。
我认为更漂亮的方法是使用scala.io.Source
:
object ScannerTest
def main(args: Array[String])
for (ln <- io.Source.stdin.getLines) println(ln)
【讨论】:
Predef 的 readLine 方法从 2.11.0 开始被废弃,现在推荐使用scala.io.StdIn
中的方法
@itemState 我的程序没有结束,如果我使用,“io.Source.stdin.getLines”将进入等待模式......如何处理......【参考方案4】:
你不能用吗
var userinput = readInt // for integers
var userinput = readLine
...
在这里可用:Scaladoc API
【讨论】:
这不等同于带有循环的代码【参考方案5】:递归版本(编译器检测尾递归以提高堆使用率),
def read: Unit =
val s = scala.io.StdIn.readLine()
println(s)
if (s.isEmpty) () else read
注意 Scala 2.11 中 io.StdIn
的使用。另请注意,使用这种方法,我们可以将用户输入累积到最终返回的集合中——除了打印出来。即,
import annotation.tailrec
def read: Seq[String]=
@tailrec
def reread(xs: Seq[String]): Seq[String] =
val s = StdIn.readLine()
println(s)
if (s.isEmpty()) xs else reread(s +: xs)
reread(Seq[String]())
【讨论】:
【参考方案6】:正如在其他 cmets 中简要指出的,scala.Predef.readLine()
is deprecated 从 Scala 2.11.0 开始,您可以将其替换为 scala.io.StdIn.readLine()
:
// Read STDIN lines until a blank one
import scala.io.StdIn.readLine
var line = ""
do
line = readLine()
println("Read: " + line)
while (line != "")
【讨论】:
以上是关于如何逐行读取标准输入?的主要内容,如果未能解决你的问题,请参考以下文章