Java Streams和System.in

时间:2015-05-22 22:31:52

标签: java

当我使用System.in对象的Scanner方法阅读nextInt()时,它会阻止,直到我写下内容并按 Enter 。但是当我在hasNext()方法之后使用它时只有hasNext()阻塞,直到我写东西并按 Enter (或使用 ctrl + z 组合在Windows上。)

while (input.hasNext())
{
    int num = input.nextInt();
    ... do things here
}

有人可以解释这究竟是如何运作的?它是否使用\n字符或只是等我按 Enter 键?为什么我在读取文件时没有这种情况(在读取文件时没有阻塞)。 Aren他们俩都流了?

3 个答案:

答案 0 :(得分:1)

1)在你的代码中," hasNext"是阻止等待输入的那个。当" hasNext"返回,这意味着有可用的输入," next"不阻止。

来自JavaDoc for" hasNext": 此方法可能会在等待输入扫描时阻塞。

2)从文件中读取时,所有内容都在那里(在文件中),所以" hasNext"将立即返回true,直到到达文件末尾。所以没有阻止。

从System.in读取时,输入是在您键入时生成的,因此它总是等待,因为它希望您使用键盘写入更多数据。

答案 1 :(得分:0)

System.in是与在给定操作系统上运行程序的JVM进程的stdin(操作系统进程标准的文件描述符)相关联的InputStream(即流)。

史蒂文斯和拉戈的开创性工作Advanced programming in Unix Environment非常有说服力地描述了幕后发生的事情。基本上,Java实现委托给您的操作系统上的标准I / O库(大约40年前由Dennis Ritchie编写/移植!)。

标准I / O库的两个特征至关重要:

  1. 它处理流而不是文件。
  2. 它提供缓冲,这是计算机RAM中的一个中间位置,在读取输入流或输出流写入之前使用。
  3. 标准I / O库仔细选择缓冲区的默认值,并且最大限度地减少readwrite系统调用的数量,从而减少执行I所需的CPU时间/ O操作。根据缓冲的发生方式,有三种流:全缓冲,行缓冲和无缓冲。

    现在,在上面的书中,以下内容见5.4节:

      

    大多数实现默认使用以下类型的缓冲:   标准错误始终是无缓冲的。所有其他流都是行   如果它们引用终端设备则缓冲;否则,他们是完全的   缓冲的。本书中讨论的四个平台遵循这些   标准I / O缓冲的约定:标准错误是无缓冲的,   对终端设备开放的流是行缓冲,所有其他   流被完全缓冲

    这意味着默认情况下,标准输入将被阻止(好像没有任何反应),直到您按下换行符。如果您重定向文件中的输入(例如java MyProgram < foo.txt),那么您正在读取默认情况下完全缓冲的流。

    这里有一些低级细节,但是当程序从终端设备读取时,它会阻止换行字符或EOF字符被按下以刷新缓冲区。从文件读取时,由于流是完全缓冲的,因此当程序开始读取缓冲区时,您不会注意到缓冲区已填满并刷新。读取EOF时,hasNext()都会返回false。

答案 2 :(得分:-1)

在Java中读到EOF

import java.util.Scanner;

public class EndOfFile 
{
    public static void main(String[] args) 
       {
               Scanner sc = new Scanner(System.in);
               for(int i = 1; sc.hasNext()== true; i++)
              {
               System.out.println(i + " " + sc.nextLine());
              }
    }
}