System.in中的read()方法
大家先来看例如以下这个程序
public class TestInputStream {
public static void main(String args[]) throws IOException {
InputStream in = System.in;
int a = in.read();
System.out.println(a);
a = in.read();
System.out.println(a);
a = in.read();
System.out.println(a);
}
}
问题一:假设输入”a“,那么会输出什么呢?
其实我输入“a”,它并没有反应
问题二:假设输入“a”并按下了回车。那么会输出什么呢?
97 13 10,而且程序结束执行
问题三:假设仅仅按下回车。那么会输出什么呢?
13 10。而且程序未结束执行
问题四:假设输出“abc”。那么会输出什么呢?
97 98 99
好了,样例将完了,以下来分析下上面4种情况
首先我们须要知道System.in究竟是什么?
直接输出System.in我们能够发现它是一个BufferedInputStream
那么BufferedInputStream.read()是怎样运作的?
我们能够粗略的扫一下源代码
private void fill() throws IOException {
byte[] buffer = getBufIfOpen();
if (markpos < 0)
pos = 0; /* no mark: throw away the buffer */
else if (pos >= buffer.length){ /* no room left in buffer */
// 这里是设置了mark之后的操作,不须要关心
}
count = pos;
int n = getInIfOpen().read(buffer, pos, buffer.length - pos);
if (n > 0)
count = n + pos;
}
当中buffer是BufferedInputStream的缓冲区,read(byte[] b, int off, int len)方法是从底层输入流读取数据,该方法为堵塞方法。那么什么时候会返回呢?
调试进去发现。System.in中底层输入流为FileInputStream。依据官方文档上的描写叙述:
1、假设 len 不为 0,则在输入可用之前,该方法将堵塞
2、返回读入缓冲区的字节总数,假设由于已经到达文件末尾而没有很多其它的数据。则返回 -1。
那么对于控制台输入该怎样推断达到“文件末尾”呢?通过回车来提交数据。并告诉程序提交完成。
以下针对上面的问题一一解答
1、因为在控制台输入时,按下回车键才代表输入完毕,输入的内容才会提交到read()方法,所以按下回车之前,程序是不知道你输入了什么的
2、输入"a"后按下回车,这时候read()方法读到了数据,此时buffer中的数据应该是97 13 10,也就是字符'a','\r', '\n'。而且read()方法每次仅仅能从缓冲区中读出一个字符,三次read()就刚好读出这3个字符。之后程序就结束了。
3、仅仅按下回车,此时从流中仅仅读到了"\r"和"\n",因为没有足够的输入。那么第三次调用read()时堵塞
4、输入"abc",此时从流中读到"a","b","c","\r","\n"。因为仅仅read()了3次。那么读出abc,\r和\n仍在buffer中
System.in中的read()方法的更多相关文章
- Java中 System.arraycopy() 和 Arrays.copyOf()方法
System.arraycopy() 和 Arrays.copyOf()方法 阅读源码的话,我们就会发现 ArrayList 中大量调用了这两个方法.比如:我们上面讲的扩容操作以及add(int in ...
- 通过实现System.IComparable接口的CompareTo方法对两个类进行比较
假设现在有一个学生类 class Student { int age; public Student(int age) { this.age = age; } } 要使学生类之间能进行比较,实现Sys ...
- C#中DataTable中的Compute方法使用收集
原文: C#中DataTable中的Compute方法使用收集 Compute函数的参数就两个:Expression,和Filter. Expresstion是计算表达式,关于Expression的详 ...
- Java中是否可以调用一个类中的main方法?
前几天面试的时候,被问到在Java中是否可以调用一个类中的main方法?回来测试了下,答案是可以!代码如下: main1中调用main2的主方法 package org.fiu.test; impor ...
- 浅谈Java中的hashcode方法
哈希表这个数据结构想必大多数人都不陌生,而且在很多地方都会利用到hash表来提高查找效率.在Java的Object类中有一个方法: 1 public native int hashCode(); 根据 ...
- Request中的各种方法
前言 Request中方法众多,对于Java Web程序员来说,种种方法都会在工作中常常用到.Request由于不是JDK的一部分,这些方法的用法也没有专门的API可以查,所以在工作中遇到Reques ...
- Java中“==”与equals方法的区别
1. 用“==”比较两个变量,如果两个变量是基本类型变量,且都是数值类,则值相等就返回true 如果两个变量是引用型变量,则两个对象的地址一样,即指向同一个对象,则返回true 2.equals:St ...
- C#中==与Equals方法的区别
using System;using System.Collections.Generic;using System.Linq;using System.Text; namespace Console ...
- TextView和EditText中的setFilters方法说明
在TextView中有一个方法public void setFilters(InputFilter[] filters),API中有一句说明:Sets the list of input filter ...
随机推荐
- LibRec:一个实现推荐系统的Java库包
LibRec是一个用于实现推系统 RS 的Java库包,实现推荐系统的两个经典问题: rating prediction(评分排行预测) 和 item ranking (项目排行),其内置了经典的机器 ...
- 使用C#开发ActiveX控件[new]
文章出处:http://www.cnblogs.com/yilin/p/csharp-activex.html 前言 ActiveX控件以前也叫做OLE控件,它是微软IE支持的一种软件组件或对象,可以 ...
- springboot 整合 rabbitmq
http://blog.720ui.com/2017/springboot_06_mq_rabbitmq/
- Python 爬虫实例(5)—— 爬取爱奇艺视频电视剧的链接(2017-06-30 10:37)
1. 我们找到 爱奇艺电视剧的链接地址 http://list.iqiyi.com/www/2/-------------11-1-1-iqiyi--.html 我们点击翻页发现爱奇艺的链接是这样的 ...
- Python操作redis系列以 哈希(Hash)命令详解(四)
# -*- coding: utf-8 -*- import redis #这个redis不能用,请根据自己的需要修改 r =redis.Redis(host=") 1. Hset 命令用于 ...
- [Jobdu] 题目1544:数字序列区间最小值
题目描述: 给定一个数字序列,查询任意给定区间内数字的最小值. 输入: 输入包含多组测试用例,每组测试用例的开头为一个整数n(1<=n<=100000),代表数字序列的长度.接下去一行给出 ...
- 【高并发简单解决方案】redis缓存队列+mysql 批量入库+php离线整合
原文出处: 崔小拽 需求背景:有个调用统计日志存储和统计需求,要求存储到mysql中:存储数据高峰能达到日均千万,瓶颈在于直接入库并发太高,可能会把mysql干垮. 问题分析 思考:应用网站架构的衍化 ...
- 自己构造用于异步请求的JSON数据
有时候.serialize()或者.serializeJSON()莫名其妙的不能按照我们的要求将数据序列化. 或者其他什么问题然我们需要自己惊醒JSON数据的构造.因为js对JSON的支持做的比较好, ...
- 【Code::Blocks】windows 环境下编译 Code::Blocks(已修正)
Code::Blocks 在2012-11-25发布了最新的12.11版本,相比上一个版本(10.05),Code::Blocks 进行了许多改进和更新(Change log). 引用 Wikiped ...
- Xml解析之PULL解析 例1
<?xml version="1.0" encoding="UTF-8"?> <persons> <person id=" ...