基础
I/O
可以分为广义的两大类别:
File I/O
和
Stream I/O
。相应地有两种类型的通道,它们是文件(
file
)通道和套接字(
socket)通道。
文件通道有一个
FileChannel
类;套接字通道有三个
类:
SocketChannel
、
ServerSocketChannel
和
DatagramChannel
。
FileChannel:从文件中读写数据。
DatagramChannel:能通过UDP读写网络中的数据。
SocketChannel:能通过TCP读写网络中的数据。
ServerSocketChannel:可以监听新进来的TCP连接,像Web服务器那样。对每一个新进来的连接都会创建一个SocketChannel。
通道可以以多种方式创建。Socket 通道有可以直接创建新 socket 通道的工厂方法。但是一个
FileChannel
对象却只能通过在一个打开的
RandomAccessFile
、
FileInputStream
或
FileOutputStream
对象上调用
getChannel( )
方法来获取。不能直接创建一个
FileChannel
对象。
1、下面例子使用FileChannel读取数据到Buffer中:
package
com;
import
java.io.FileInputStream;
import
java.io.IOException;
import
java.nio.ByteBuffer;
import
java.nio.channels.FileChannel;
public
class
Test{
public
static
void
main (String[]argv)
throws
IOException{
FileInputStream aFile =
new
FileInputStream(
"/Users/wudiyong/xxx"
);
FileChannel inChannel = aFile.getChannel();
ByteBuffer buf = ByteBuffer.allocate(
48
);
int
bytesRead = inChannel.read(buf);
while
(bytesRead != -
1
) {
System.out.println(
"Read "
+ bytesRead);
buf.flip();
while
(buf.hasRemaining()){
System.out.print((
char
) buf.get());
}
buf.clear();
bytesRead = inChannel.read(buf);
}
aFile.close();
}
}
FileInputStream会当打开文件不存在时自动创建。
2、下面例子从一个通道复制数据到另一个通道 :
import
java.io.IOException;
import
java.nio.ByteBuffer;
import
java.nio.channels.Channels;
import
java.nio.channels.ReadableByteChannel;
import
java.nio.channels.WritableByteChannel;
public
class
Test {
public
static
void
main(String[] agrs)
throws
IOException {
ReadableByteChannel source = Channels.newChannel(System.in);
WritableByteChannel dest = Channels.newChannel(System.out);
// channelCopy1(source, dest);//方式一
channelCopy2(source, dest);
//方式二
source.close();
dest.close();
}
private
static
void
channelCopy1(ReadableByteChannel src,WritableByteChannel dest)
throws
IOException {
ByteBuffer buffer = ByteBuffer.allocateDirect(
16
*
10
);
while
(src.read(buffer) != -
1
) {
buffer.flip();
dest.write(buffer);
/*
* 因为可能不能够一次把buffer全部输出,此时buffer里还有剩余的数据,需要用compact()把
* 这些数据往前移,新的数据才能从后面写入,如果一次就能完全输出,则compact的作用相当于clear
*/
buffer.compact();
}
//可能buffer里还有数据,把剩余的数据全部输出
buffer.flip();
while
(buffer.hasRemaining()) {
dest.write(buffer);
}
}
private
static
void
channelCopy2(ReadableByteChannel src,WritableByteChannel dest)
throws
IOException{
ByteBuffer buffer = ByteBuffer.allocateDirect (
16
*
10
);
while
(src.read (buffer) != -
1
) {
buffer.flip();
//循环把buffer里的所有数据都输出,再接收新的数据
while
(buffer.hasRemaining()){
dest.write (buffer);
}
buffer.clear( );
}
}
}
通道
版权声明:本文为博主原创文章,未经博主允许不得转载。
- 上一篇线程的阻塞
- 下一篇Fork/Join并行框架