java的nio之:java的nio系列教程之SocketChannel
Java NIO中的SocketChannel是一个连接到TCP网络套接字的通道。可以通过以下2种方式创建SocketChannel:
- 打开一个SocketChannel并连接到互联网上的某台服务器。
- 一个新连接到达ServerSocketChannel时,会创建一个SocketChannel。
打开 SocketChannel
下面是SocketChannel的打开方式:
1 |
SocketChannel socketChannel = SocketChannel.open(); |
2 |
socketChannel.connect( new InetSocketAddress( "http://jenkov.com" , 80 )); |
关闭 SocketChannel
当用完SocketChannel之后调用SocketChannel.close()关闭SocketChannel:
1 |
socketChannel.close(); |
从 SocketChannel 读取数据
要从SocketChannel中读取数据,调用一个read()的方法之一。以下是例子:
1 |
ByteBuffer buf = ByteBuffer.allocate( 48 ); |
2 |
int bytesRead = socketChannel.read(buf); |
首先,分配一个Buffer。从SocketChannel读取到的数据将会放到这个Buffer中。
然后,调用SocketChannel.read()。该方法将数据从SocketChannel 读到Buffer中。read()方法返回的int值表示读了多少字节进Buffer里。如果返回的是-1,表示已经读到了流的末尾(连接关闭了)。
写入 SocketChannel
写数据到SocketChannel用的是SocketChannel.write()方法,该方法以一个Buffer作为参数。示例如下:
01 |
String newData = "New String to write to file..." + System.currentTimeMillis(); |
02 |
03 |
ByteBuffer buf = ByteBuffer.allocate( 48 ); |
04 |
buf.clear(); |
05 |
buf.put(newData.getBytes()); |
06 |
07 |
buf.flip(); |
08 |
09 |
while (buf.hasRemaining()) { |
10 |
channel.write(buf); |
11 |
} |
注意SocketChannel.write()方法的调用是在一个while循环中的。Write()方法无法保证能写多少字节到SocketChannel。所以,我们重复调用write()直到Buffer没有要写的字节为止。
非阻塞模式
可以设置 SocketChannel 为非阻塞模式(non-blocking mode).设置之后,就可以在异步模式下调用connect(), read() 和write()了。
connect()
如果SocketChannel在非阻塞模式下,此时调用connect(),该方法可能在连接建立之前就返回了。为了确定连接是否建立,可以调用finishConnect()的方法。像这样:
1 |
socketChannel.configureBlocking( false ); |
2 |
socketChannel.connect( new InetSocketAddress( "http://jenkov.com" , 80 )); |
3 |
4 |
while (! socketChannel.finishConnect() ){ |
5 |
//wait, or do something else... |
6 |
} |
write()
非阻塞模式下,write()方法在尚未写出任何内容时可能就返回了。所以需要在循环中调用write()。前面已经有例子了,这里就不赘述了。
read()
非阻塞模式下,read()方法在尚未读取到任何数据时可能就返回了。所以需要关注它的int返回值,它会告诉你读取了多少字节。
非阻塞模式与选择器
非阻塞模式与选择器搭配会工作的更好,通过将一或多个SocketChannel注册到Selector,可以询问选择器哪个通道已经准备好了读取,写入等。Selector与SocketChannel的搭配使用会在后面详讲。
java的nio之:java的nio系列教程之SocketChannel的更多相关文章
- Spring 系列教程之 bean 的加载
Spring 系列教程之 bean 的加载 经过前面的分析,我们终于结束了对 XML 配置文件的解析,接下来将会面临更大的挑战,就是对 bean 加载的探索.bean 加载的功能实现远比 bean 的 ...
- SpringBoot系列教程之Bean加载顺序之错误使用姿势辟谣
在网上查询 Bean 的加载顺序时,看到了大量的文章中使用@Order注解的方式来控制 bean 的加载顺序,不知道写这些的博文的同学自己有没有实际的验证过,本文希望通过指出这些错误的使用姿势,让观文 ...
- SpringBoot系列教程之Bean之指定初始化顺序的若干姿势
上一篇博文介绍了@Order注解的常见错误理解,它并不能指定 bean 的加载顺序,那么问题来了,如果我需要指定 bean 的加载顺序,那应该怎么办呢? 本文将介绍几种可行的方式来控制 bean 之间 ...
- kali linux 系列教程之metasploit 连接postgresql可能遇见的问题
kali linux 系列教程之metasploit 连接postgresql可能遇见的问题 文/玄魂 目录 kali linux 下metasploit 连接postgresql可能遇见的问题. ...
- kali Linux系列教程之BeFF安装与集成Metasploit
kali Linux系列教程之BeFF安装与集成Metasploit 文/玄魂 kali Linux系列教程之BeFF安装与集成Metasploit 1.1 apt-get安装方式 1.2 启动 1. ...
- Kali Linux系列教程之OpenVas安装
Kali Linux系列教程之OpenVas安装 文 /玄魂 目录 Kali Linux系列教程之OpenVas安装 前言 1. 服务器层组件 2.客户层组件 安装过程 Initial setup ...
- RabbitMQ系列教程之二:工作队列(Work Queues)(转载)
RabbitMQ系列教程之二:工作队列(Work Queues) 今天开始RabbitMQ教程的第二讲,废话不多说,直接进入话题. (使用.NET 客户端 进行事例演示) ...
- WCF系列教程之WCF服务协定
本文参考自:http://www.cnblogs.com/wangweimutou/p/4422883.html,纯属读书笔记,加深记忆 一.服务协定简介: 1.WCF所有的服务协定层里面的服务接口, ...
- WCF系列教程之WCF服务宿主与WCF服务部署
本文参考自http://www.cnblogs.com/wangweimutou/p/4377062.html,纯属读书笔记,加深记忆. 一.简介 任何一个程序的运行都需要依赖一个确定的进程中,WCF ...
随机推荐
- PAT 08-2 求矩阵的局部最大值
这题挺简单的,但,每日一篇.说两点:第一,我的粗心导致我这题花了大把的时间去找错误,看到4个测试用例对了三个,我以为是那块的边界条件没考虑到,又或者是存在隐蔽的逻辑或语法错误,通过与别人程序的反复对比 ...
- fwrite错误
使用fwrite出错 f:\dd\vctools\crt_bld\self_x86\crt\srt\write.cline:69expression:_osfile(fh)&FOPEN 使用w ...
- [转]dev C++编写windows程序遇到问题
1.工具-编译选项-编译器-在连接器命令行加入以下命令: -mwindows 2.出现错误:undefined reference to `PlaySoundA@12' 解决办法:工具-编译选项-编译 ...
- bistu新生-1004
#include "stdio.h"#include "stdlib.h"#include "math.h"int cmp(const vo ...
- SQL Server LEFT Functions
LEFT(string, n)函数,是处理字符数据获取子字符串.第一个参数是将要处理的字符串,第二个参数,是从字符串的左边开始截取的字符个数. 例子: DECLARE @string NVARCHAR ...
- php大力力 [014节] 八杆子打不着的非技术文章,哈哈
今天似乎是个值得纪念的日子 一个创业失败者的忠告:请不要再参加创业活动 PHP mysql_connect() 函数 mysql默认用户 随意发几个链接,没任何意义
- BZOJ 2331 地板
妈妈我会写插头dp了!!!!!!.... 感动啊... #include<iostream> #include<cstdio> #include<cstring> ...
- linux下vi命令
Vi共分三种模式,分别是“一般模式”.“编辑模式”与“命令行命令模式”. 1.一般模式:vi处理文件时,一进入该文件就是一般模式.在这个模式中,可以使用“上下左右”键来移动光标,可以使用“删除字符”或 ...
- Linux基础入门(新版)(实验五至实验八)
实验五 环境变量与文件查找 (环境变量的作用与用法,及几种搜索文件的方法) 一.环境变量 1.变量 (1)常变量与值是一对一的关系 (2)变量的作用域即变量的有效范围(比如一个函数中.一个源文 ...
- HDU 3605
http://acm.hdu.edu.cn/showproblem.php?pid=3605 用最大流做的,G++超时,C++可以过,看别人写的叫二分图多重匹配,还不会这玩意一会学学 显然的最大流模型 ...