read()方法返回的是下一个数据字节。一个字节的对应的int型范围是0~255。所以当然read方法当读到数据结尾时返回-1代表着数据读完了。而不是你所想的返回就是4,这个返回值是不固定是根据下一个数据字节来返回0~255之间的int型数值。作者: 李保成 时间: 2012-5-8 06:30
简单理解一下,就是read()返回的是单个字节,byte类型的长度是-128-----127.我们一般接收的时候使用int型接收,方便后边的操作。而如果read()到下一个字节时,这个位置为空时,它就会返回负数,而不一定就是-1。因为它的底层结构都是数组,不管返回0还是正数,为了防止有对应的角标值,我们一般是使用负数来作为返回值。以保证数据的安全性和正确性。作者: 蒋映辉 时间: 2012-5-8 07:28
一个模拟的模型:public int read(byte b){
if(字节流中有值){ 把字节流中的字节放在b中;return 一个非-1整数}
else return -1
}
所以跟你的想法不太一样作者: 赵玮_Tom 时间: 2012-5-8 07:44
建议你仔细看毕老师基础视频。
首先要知道硬盘上的数据,无论什么类型,都是以二进制形式存储的。我们知道一个字节有8个二进制数字组成,那么很有可能读到某个字节出现连续8个二进制都是1的情况,那么这个字节读出来之后就是-1。而read()方法的结束标记也是-1。这样就会导致文件还没有读完,读取流就已经认为文件结束了。为了解决这种情况的发生,需要将byte类型的数据提升为int类型,并和255(0xff)进行与运算(&),这样操作的结果就是,返回结果变为int类型,但只有后8位是有效数据,前面的24位全部是0,而且但读到8个二进制都是1的情况,是不会返回-1的,而是返回255。
当然,这是读取的数据貌似是源数据的4倍,而当调用写入流的write()方法时,会自动将int类型数据强转为byte类型,也就是说只保留最后8位的有效数据,这样可以保证文件大小不变。
简言之,就是read()方法做类型提升,write方法做强转动作。 作者: 隋营营 时间: 2012-5-8 07:47
楼主的理解有点偏差:
下面是JDK中InputSteam类的read()方法的源代码:
/**
* Reads the next byte of data from the input stream. The value byte is
* returned as an <code>int</code> in the range <code>0</code> to
* <code>255</code>. If no byte is available because the end of the stream
* has been reached, the value <code>-1</code> is returned. This method
* blocks until input data is available, the end of the stream is detected,
* or an exception is thrown.
*
* <p> A subclass must provide an implementation of this method.
*
* @return the next byte of data, or <code>-1</code> if the end of the
* stream is reached.
* @exception IOException if an I/O error occurs.
*/
public abstract int read() throws IOException;
注意红色的部分:读入的字节作为int类型的值(值范围:0-255)返回,也就是说只用了int 的低8位,高24位没用到。
再看OutputStream类的write()方法的源代码:
/**
* Writes the specified byte to this output stream. The general
* contract for <code>write</code> is that one byte is written
* to the output stream. The byte to be written is the eight
* low-order bits of the argument <code>b</code>. The 24
* high-order bits of <code>b</code> are ignored.
* <p>
* Subclasses of <code>OutputStream</code> must provide an
* implementation for this method.
*
* @param b the <code>byte</code>.
* @exception IOException if an I/O error occurs. In particular,
* an <code>IOException</code> may be thrown if the
* output stream has been closed.
*/
public abstract void write(int b) throws IOException;
注意红色部分:参数b的低8位被写入输出流,而高24位被忽略。