- InputStream:读;
- OutputStream:写;
- 字符流使用的是字符数组,字节流使用的是字节数组;
- MyBufferedInputStream
- 定义数组
- 定义指针
- 定义计数器
- mp3格式文件开头就有-1的二进制位,
- byte类型的-1提升为int类型的-1,原因是因为在8个1前面补1导致的;如果补0就可以解决这个问题。接受为什么用int不用byte, 在8个1前面补0,不补1;方法:让它与255与运算就OK!
- 读的时候类型提升了,但是写入的时候只写低八位,保证了元数据的原样性。
而其他正常byte类型的数据提升后的值与255进行按位与操作后的数值不变,这就是与255按位与操作的魅力。
在计算机中数据的存储使用补码表示的,-1的补码就是8个1或者32个1。
那问题来了,如果reader方法读到了行尾的-1怎么办,是返回-1还是返回255。
代码如下:
import java.io.*;
//创建自己的缓存器,用来缓存字节流。
class MyBufferedInputStream1{
//创建一个字节流对象;
private InputStream is;
private byte[] buf = new byte[1024*4];
private int pos, count;
MyBufferedInputStream1(InputStream it){
this.is = it;
}
//一次从缓冲区读取一个字节;
//为什么不返回byte类型呢?
//为解决开头读到八个1时,返回-1的情况;对字节进行提升,
//在前面补上0,这样就能保证数值没有变化,又能防止返回-1;
//为了在前面补0,我们就让byte类型的数据提升后和255进行按位与操作即可。
public int myRead() throws IOException{
//通过is对象读取硬盘上的数据,并存到buf中。
if(count==0) {
count = is.read(buf);
if(count<0)
//当缓存器中的字符串长度小于0时,返回-1。
return -1;
pos = 0; //如果刚好count=0,就给缓存器中的字符串附上下标。
byte b = buf[pos]; //读取一个字符
//往后面移1位,字符数量-1
count--;
pos++;
//返回int类型
return b&0xffff;
}
//如果count>0,就重复上述取值的过程。
else if(count>0) {
byte b = buf[pos];
count--;
pos++;
return b&0xffff;
}
return -1;
}
//模仿官方缓存器,写一个自己的关闭文件的快捷方法;
public void myClose()throws IOException{
is.close();
}
}
public class MyBufferedInputStream {
public static void main(String[] args) {
//调用系统中返回当前时间的函数,用来计算拷贝文件需要多长时间。
long start = System.currentTimeMillis();
try {
copy_2();
}
catch(Exception e)
System.out.println("拷贝失败!");
}
long end = System.currentTimeMillis();
System.out.println((end-start)+"ms");
}
//异常处理时,代码量很多要学会用静态函数。
public static void copy_2() throws IOException{
MyBufferedInputStream1 mbis =
new MyBufferedInputStream1(new FileInputStream("[F://MOVE_MUSIC//1.mp3](file:///F://MOVE_MUSIC//1.mp3)"));
//由于只写了自己的输入字节流缓存器,输出字节流缓存器就都用Java自己的。
BufferedOutputStream bfos =
new BufferedOutputStream(new FileOutputStream("[F://MOVE_MUSIC//2.mp3](file:///F://MOVE_MUSIC//2.mp3)"));
System.out.println("第一个字节:"+mbis.myRead());
int by = 0;
//虽然有缓存器,但缓存器其实就是字节流对象的装饰类,还是每次只能读取一位;
//要想一行一行的读写数据,还是要用while循环实现。
while((by=mbis.myRead())!= -1) {
bfos.write(by);
}
mbis.myClose();
bfos.close();
}
}
网友评论