Java 两个版本的扫描仪之间有什么区别?
从控制台读取输入的这些方法之间有什么区别Java 两个版本的扫描仪之间有什么区别?,java,input,console,Java,Input,Console,从控制台读取输入的这些方法之间有什么区别 Scanner in = new Scanner(new BufferedReader(new InputStreamReader(System.in))); 及 那么优点和缺点是什么?我认为回答这些问题的最好方法是检查实际实现的来源。您可以从这里下载源代码:或者只下载特定于Google的类:“java.util.Scanner source” 在这种情况下,匹配源: public Scanner(InputStream source) { th
Scanner in = new Scanner(new BufferedReader(new InputStreamReader(System.in)));
及
那么优点和缺点是什么?我认为回答这些问题的最好方法是检查实际实现的来源。您可以从这里下载源代码:或者只下载特定于Google的类:“java.util.Scanner source” 在这种情况下,匹配源:
public Scanner(InputStream source) {
this(new InputStreamReader(source), WHITESPACE_PATTERN);
}
您可以使用此代码段实现相同的功能:
Scanner in = new Scanner(new BufferedReader(new InputStreamReader(new BufferedInputStream(System.in))));
扫描仪
构造函数
就目前的情况来看,两者没有太大区别
您使用的Scanner
的第一个构造函数Scanner(Readable)
,将表示字符传入序列的对象作为参数,可以使用字符缓冲区
读取该序列
您使用的Scanner
的第二个构造函数是Scanner(InputStream)
,它将表示传入的字节序列的对象作为参数
应该强调的是,字节不是字符。字符可以由不同的字节序列表示,具体取决于字符编码,并且每个字符可以跨越一个以上的字节
在内部,第二个构造函数立即用InputStreamReader
包装参数,这是一个提供字符数据的可读的
,因此与使用第一个构造函数几乎相同
BufferedInputStream
vsBufferedReader
因此,仍然存在的差异是
new BufferedReader(new InputStreamReader(System.in))
及
它们读取数据的方式略有不同
第一个链将在每次需要输入时填充8192个字符的缓冲区,从底层读卡器获取每个字符,该读卡器将从System.in
的字节中对其进行解释
第二个链将在每次需要输入时填充8192字节的缓冲区。因此,当包装读取器需要下一个字符时,假设该字符在输入中由两个字节表示,而当前缓冲区中只有该字符的一个字节。第二个字节将需要再次填充缓冲区
我没有经验数据,但我认为,考虑到扫描器
每次需要数据时都会填充字符缓冲区
,上述细微差别将是相当微不足道的。事实上,我相信您可以安全地放弃使用BufferedReader
或BufferedInputStream
,只需将InputStreamReader
或系统直接送入扫描仪,它将负责缓冲
指定输入的字符集
如果需要使用特定的字符集进行输入,则会有所不同。例如,如果要确保传入的字节流被解释为UTF-8
,可以使用:
Scanner in = new Scanner(new InputStreamReader(System.in,StandardCharsets.UTF_8));
否则,输入字节将被解释为默认字符集,该字符集不一定是UTF-8
扫描器
还有另一个构造函数,它也允许使用普通的输入流
:
Scanner in = new Scanner(System.in, "UTF-8");
这也将包装系统。在
中,立即使用InputStreamReader
,因此差别不大。扫描仪
只有1024个字符的缓冲区,添加一个缓冲区…
会添加8192个字符/字节的底层缓冲区。因此,如果您正在读取大量数据(例如文件),这是有区别的,但我认为如果您正在读取较小的输入(例如控制台输入),则没有优势
Scanner in = new Scanner(new InputStreamReader(System.in,StandardCharsets.UTF_8));
Scanner in = new Scanner(System.in, "UTF-8");