当前位置: 首页 > 科技观察

为什么你总是不懂JavaIO流?这是我用过最好用的工具

时间:2023-03-21 17:58:07 科技观察

大家好,我说的是北君,今天我们来说说java中的IO流和Guava。在GuavaIO的日常系统交互中,文件的上传和下载是很常见的。一般我们会通过jdk提供的IO操作库帮我们实现。IO指的是数据相对于当前运行程序的进出。数据通过输出流从程序输出,或者数据(来自文件、网络、数据等)通过输入流写入程序。这里的IO是指Streams作为数据传输的载体。如果把数据比作合理的水,河流就是IO流,就是数据的载体。Java为我们提供了很多操作IO的接口和类,帮助开发者实现不同来源之间的数据传输,比如硬盘文件、网络传输、应用程序调用之间的数据交互和中转。今天,我们就简单了解一下Java中的流程以及Guava工具包中对IO操作的封装和设计。分类java.io包中有很多IO相关的接口。我们可以根据流的输出类型、处理对象和功能将它们分为以下几种:根据数据流向输入流(java.io.InputStream)实现将数据读入程序输出流(java.io.InputStream)。io.OutputStream)用于实现从程序中写出数据,以字节(byte)为操作单位读写数据(文件也提供了根据基本数据类型读写的DataInpoutStream,即,根据Java基本类型占用的字节数进行定量字节读取和合并)字符流以字符(char)为单位读写数据。需要注意字符编码的区别:字节流一般以Stream结尾,字符流一般以Reader或Writer结尾。读操作方式(java.io.Reader)主要是针对字符流的读操作。write(java.io.Writer)主要是针对字符流的写操作,按函数缓存流和按字节读写数据,通过缓冲批量写入提高传输效率,转换流实现之间的转换输入/输出和读/写。.io.FileinputStream/FileOutputStreamjava.io.FileReader/FileWriter普通字节流java.io.InputStreamReader/outputStreamWriter缓冲流java.io.BufferedReader/BufferedWriterjava.io.BufferedInputStream/BufferedOutputStream数据流java.io.DataInpoutStream/DataOutputStreamFunctionaljava.io.PrintWriter/PrintStream对象序列化相关的java.io.ObjectInputStream/ObjectOutputStream可以看出,提供的IO对象基本都是成对出现,完成数据的输入输出,实现程序与外部载体的通信。通过一些常见的例子看一下IO的场景和使用方法:文件复制,文件合并,将文件内容读成字符串,字节数组,转换成流对象,流转换的序列化和反序列化...文件复制@TestpublicvoidcopyByBytes()抛出IOException{Stringroot=FileTests.class.getResource("/").getPath();FileInputStreamfis=newFileInputStream(newFile(root,"/start.bat"));FileOutputStreamfos=newFileOutputStream(root+"/out2.bat");byte[]buff=newbyte[100];诠释乙;while((b=fis.read(buff))!=-1){fos.write(buff,0,b);}//close}文件合并@TestpublicvoidmergeFiles()throwsIOException{Filefile1=newFile("E:\\_projects\\sucls\\blog\\my_study\\guava\\guava-io\\src\\test\\java\\com\\sucls\\blog\\guava\\io\\category\\FileTests.java");Filefile2=newFile("E:\\_projects\\sucls\\blog\\my_study\\guava\\guava-io\\src\\test\\java\\com\\sucls\\blog\\guava\\io\\类别\\StreamTests.java");Enumerationins=Collections.enumeration(Arrays.asList(newFileInputStream(file1),newFileInputStream(file2)));SequenceInputStream序列eInputStream=newSequenceInputStream(ins);FileOutputStreamfos=newFileOutputStream(root+"/out4");byte[]buff=newbyte[100];诠释阅读;//实际读取的字节数while((read=sequenceInputStream.read(buff))!=-1){fos.write(buff,0,read);}fos.close();}以字符串形式读取文件内容@TestpublicvoidreadStringFromFile()throwsIOException{FileReaderfileReader=newFileReader(newFile(this.getClass().getResource("/").getPath(),"/start.蝙蝠”));StringBuilderstringBuilder=newStringBuilder();诠释我;while((i=fileReader.read())!=-1){stringBuilder.append((char)i);//按字符读取}System.out.println(stringBuilder);//文件内容}字节数组转换为流@测试publicvoidbytesToStream(){byte[]data=newbyte[1024];//来自其他数据源ByteArrayInputStreaminputStream=newByteArrayInputStream(data);ByteArrayOutputStreamoutputStream=newByteArrayO输出流();诠释五;while((v=inputStream.read())!=-1){outputStream.write(v);}System.out.println(Arrays.toString(outputStream.toByteArray()));}对象序列表化与反序列化@TestpublicvoidobjectToFile()throwsIOException{Personperson=newPerson();person.setName("张三").setAge(25);Stringroot=FileTests.class.getResource("/").getPath();FileOutputStreamfos=newFileOutputStream(newFile(root,"/person"));ObjectOutputStreamoos=newObjectOutputStream(fos);oos.writeObject(人);}@TestpublicvoidfileToObject()throwsIOException,ClassNotFoundException{Stringroot=FileTests.class.getResource("/").getPath();FileInputStreamfis=newFileInputStream(newFile(root,"/person"));ObjectInputStreamois=newObjectInputStream(fis);Personperson=(Person)ois.readObject();System.out.println(人);}流的转换将字节流转换成字符流进行操作,同样以文件拷贝为例FileInputStreamfis=newFileInputStream(newFile(root,"/start.bat"));InputStreamReaderisr=newInputStreamReader(fis);BufferedReaderbr=newBufferedReader(isr);FileOutputStreamfos=newFileOutputStream(root+"/out3.bat");OutputStreamWriterosw=newOutputStreamWriter(fos);BufferedWriterbw=newBufferedWriter(osw);弦线;while((line=br.readLine())!=null){bw.追加(行);体重。新队();体重。冲洗();}//close}流操作有很多,比如网络通信、音视频文件处理、流合并等,Guava中IO的内容并不复杂。以上例子在很多工具库中基本上都会提供相应的API供开发者调用。今天主要看一下GuavaIO模块对流操作提供了什么样的封装。文件提供了读取和写入文件的快速方法。主要提供了ByteSource、ByteSink、CharSource、CharSink。类,对应字节读写和字符读写,/***文件复制*/@Testpublicvoidcopy()throwsIOException{Filefrom=newFile(root,"from");文件到=新文件(根,“到”);文件复制(从,到);}/***文件移动*/@Testpublicvoidmove()throwsIOException{Filefrom=newFile(root,"from");文件到=新文件(根,“到”);文件.移动(从,到);}/***按行读取文件*@throwsIOException*/@TestpublicvoidreadLines()throwsIOException{Filedest=newFile(root,"start.bat");Listlines=Files.readLines(dest,Charset.defaultCharset());lines.forEach(System.out::println);}/***写入文件*@throwsIOException*/@TestpublicvoidwriteToFile()throwsIOException{Filedest=newFile(root,"demo.txt");Files.write("helloworld!".getBytes(Charset.defaultCharset()),dest);}/***修改文件更新时间*@throwsIOException*/@Testpublicvoidtouch()throwsIOException{Filedest=newFile(root,"demo.txt");Files.touch(目标);}/***文件的零副本*@throwsIOException*/@Testpublicvoidmap()throwsIOException,URISyntaxException{Filefrom=newFile(root,"from");文件到=新文件(根,“到”);文件.触摸(到);MappedByteBufferfromBuff=Files.map(from,MapMode.READ_ONLY,1024);//=>FileChannelchannel=FileChannel.open(Paths.get(to.toURI()),StandardOpenOption.WRITE);channel.write(fromBuff);通道关闭();}/***将文件读取为字节数组*@throwsIOException*/@TestpublicvoidfileAndBytes()throwsIOException{Filedest=newFile(root,"start.bat");ByteSourcebyteSource=Files.asByteSource(dest);byte[]bytes=byteSource.read();System.out.println(bytes);//向文件写入字节,实现复制Filetarget=newFile(root,"start2.bat");ByteSinkbyteSink=Files.asByteSi文件nk(target);byteSink.write(bytes);}@Testpublicvoidwrapper(){Filedest=newFile(root,"start.bat");//ReadFilesasbytes.asByteSource(dest);//WriteasbytesFiles.asByteSink(dest);//ReadascharactersFiles.asCharSource(dest,Charset.defaultCharset());//WriteascharactersFiles.asCharSink(dest,Charset.defaultCharset());}Other管道流PipedOutputStreamPipedInputStream实现多线程间的数据通信;类似生产消费者模式@Testpublicvoidpipe()throwsIOException{PipedOutputStreampipedOutputStream=newPipedOutputStream();PipedInputStreampipedInputStream=newPipedInputStream();pipedOutputStream.connect(pipedInputStream);newThread(()->{while(true){Stringdate=newDate().toString();try{pipedOutputStream.write(date.getBytes(StandardCharsets.UTF_8));pipedOutputStream.flush();TimeUnit.秒。睡觉(2);}catch(IOExceptione){thrownewRuntimeException(e);}catch(InterruptedExceptione){thrownewRuntimeException(e);}}})。开始();newThread(()->{while(true){byte[]buff=newbyte[1024];try{intread=pipedInputStream.read(buff);TimeUnit.SECONDS.sleep(4);}catch(IOExceptione){thrownewRuntimeException(e);}catch(InterruptedExceptione){thrownewRuntimeException(e);}System.out.println(newString(buff));}}).start();}结语在任何编程语言中,dataIO作为一个工具类库都是比较常见和相当重要的,主要是帮助开发者封装常见和重复的操作,并开放一个简短的API,不仅让代码更整洁,而且也是健壮程序开发无法比拟的。较少的。

最新推荐
猜你喜欢