java NIO 简介

一、IO和NIO的区别

1、io和nio无非是对数据进行读取和写入操作,但是io是将流中的数据读取到内存,或者写入到磁盘。而nio是将通道channel中的数据读取到缓冲区buffer或者,将buffer的数据写入到channel中。
(1)、进行io操作时,如读取文件,io会处于阻塞状态直到有数据可读。此时cpu多数时间处于空闲状态,浪费了cpu时间片的资源。而Nio可以设置channel为非阻塞状态,并且可以开启多个线程同时进行读写操作,此时节约cpu时间片的资源,但是cpu一直运转增大了内存消耗,并且增大了线程切换的开销。每个线程内部都是一个私有的程序计数器,会记录程序运行的位置,从而保证线程顺利切换。

(2)、Nio大大提高了io的执行速度。Nio可以同时将一个channel中的数据读入到多个Buffer中,也可以同时多个Buffer中的数据同时写入到同一个channel中。并且Nio的选择器Selector在开启一个线程的情况下,可以同时注册多个channel并对其监控。而io实现这个功能则需要开启多个线程。

二、io部分基础复习

1、RandomAccessFile、File的使用

RandomAccessFile是一个具有强大功能来操作文件的类

(1)复制文件

<span style="font-family:KaiTi_GB2312;">package testFile;

import java.io.File;
import java.io.RandomAccessFile;

public class TestRandomAccessFile {

	public static void main(String[] args) throws Exception {
		File file1 = new File("file1.txt");
		File file2 = new File("file2.txt");
		copyFile(file1, file2);
	}

	public static void copyFile(File file1, File file2) throws Exception {
		if (!file2.exists()) {
			file2.createNewFile();
		}
		RandomAccessFile rf1 = new RandomAccessFile(file1, "r");//r只读模式获取
		RandomAccessFile rf2 = new RandomAccessFile(file2, "rw");//读写模式获取
		
		rf1.getFilePointer();//获取当前指针的位置
		rf1.seek(11);//设置指针位置为11,读取时会从指针当前位置开始
		
		byte[] content = new byte[48];
		int len = 0;//有效长度
		while((len = rf1.read(content)) != -1) {
			rf2.write(content,0,len);
		}
		rf2.close();
		rf1.close();
	}
}
</span>

file1.txt文件内容为:

hello wolrd

这是演示文本!!!

file2.txt文件内容为:


这是演示文本!!!

这是因为指针刚好移动11个字节,从第二行开始读取。

(2)、通过File遍历目录下的所有子目录并输出

<span style="font-family:KaiTi_GB2312;">public class TestFile {

	public static void main(String[] args) {
		String fileName = "F:\\aspectj-1.8.9\\$installer$";
		File file = new File(fileName);
		listFile(file);
	}

	public static void listFile(File file) {
		if(file.isDirectory()) {
			File[] files = file.listFiles();
			for(File f:files) {
				listFile(f);
			}
		}else {
			System.out.println(file.getName());
		}
	}
}</span>

(3)、多个线程间用io流进行通信

<span style="font-family:KaiTi_GB2312;">package testFile;

import java.io.IOException;
import java.io.PipedInputStream;
import java.io.PipedOutputStream;
import java.util.Scanner;

public class TestPiped {

	public static void main(String[] args) {

		Sender sender = new Sender();
		Receiver receiver = new Receiver();
		
		try {
			//对象初始化之后,将这两个流通过connect连接成一个管道
			receiver.pStream.connect(sender.pStream);
		} catch (IOException e) {
			System.out.println(e.getMessage());
		}
		
		sender.start();
		receiver.start();
	}
}

class Sender extends Thread {

	PipedOutputStream pStream = null;

	public Sender() {
		pStream = new PipedOutputStream();
	}

	@Override
	public void run() {
		System.out.print("請輸入要說的:");
		Scanner sc = new Scanner(System.in);
		String msg = sc.nextLine();
		try {
			pStream.write(msg.getBytes());
		} catch (IOException e) {
			System.out.println(e.getMessage());
		}
	}
}

class Receiver extends Thread {

	PipedInputStream pStream = null;

	public Receiver() {
		pStream = new PipedInputStream();
	}

	@Override
	public void run() {
		try {
			byte[] b = new byte[1024];
			int len = 0;
			while ((len = pStream.read(b)) != -1) {
				System.out.println(new String(b, 0, len) + "这是该线程接收到的数据");
			}
		} catch (IOException e) {
			System.out.println(e.getMessage());
		}
	}
}</span>

测试结果:

請輸入要說的:管道流測試數據
管道流測試數據这是该线程接收到的数据
Write end dead

三、Nio核心知识

缓冲区Buffer、通道Channel、选择器Selector将在后面依次介绍。





  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值