java 异步socket_java Socket读写异步分离
在Android开发中,基于Socket的通信必须是非阻塞式的,因此需要Reader和Writer异步分离,此外需要监听Socket网络状态、
监听接口
package com.io.sockets;
import java.io.IOException;
import java.net.Socket;
public interface SocketStatusListener
{
public static final int STATUS_OPEN = 0x01<<0;
public static final int STATUS_CLOSE = 0x01<<1;
public static final int STATUS_RESET = 0x01<<2;
public static final int STATUS_PIP_BROKEN = 0x01<<3;
public static final int STATUS_UNKOWN = 0x01<<4;
public void onSocketStatusChanged(Socket socket,int status,IOException e);
}
Handler读写处理控制
package com.io.sockets;
import java.io.IOException;
import java.net.Socket;
public class SocketHandler implements SocketStatusListener {
private Socket socket=null;
private ReaderTask reader;
private WriterTask writer;
public SocketHandler(Socket socket) throws IOException {
this.socket = socket;
this.socket.setTcpNoDelay(true);
reader = new ReaderTask(socket);
writer = new WriterTask(socket);
onSocketStatusChanged(socket, STATUS_OPEN, null);
}
/**
* sendMessage:(这里用一句话描述这个方法的作用).
* TODO(这里描述这个方法适用条件 – 可选).
*/
public void sendMessage(String msg) {
writer.send(msg);
}
public void listen(boolean isListen)
{
reader.startListener(this);
}
public void shutDown() {
if(!socket.isClosed() &&socket.isConnected())
{
try {
writer.finish();
reader.finish();
socket.close();
} catch (IOException e) {
e.printStackTrace();
onSocketStatusChanged(socket, STATUS_CLOSE, e);
}finally{
reader = null;
writer = null;
System.out.println("Socket连接已关闭!!");
}
}
}
@Override
public void onSocketStatusChanged(Socket socket,int status, IOException e) {
switch (status) {
case SocketStatusListener.STATUS_CLOSE:
case SocketStatusListener.STATUS_RESET:
case SocketStatusListener.STATUS_PIP_BROKEN:
shutDown();
break;
default:
break;
}
}
}
读取任务
package com.io.sockets;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.Socket;
import java.net.SocketException;
public class ReaderTask extends Thread{
private SocketStatusListener socketStatusListener;
private BufferedReader bufferedReader;
private Socket socket;
private boolean listening;
public ReaderTask(Socket socket) throws IOException
{
bufferedReader = new BufferedReader(new InputStreamReader(socket.getInputStream()));
this.socket = socket;
}
/**
* finish:(这里用一句话描述这个方法的作用).
* TODO(这里描述这个方法适用条件 – 可选).
* @throws IOException
*
*/
public void finish() throws IOException
{
listening = false;
interrupt();
if(bufferedReader!=null && socket!=null)
{
if(socket.isInputShutdown())
{
socket.shutdownInput();
}
bufferedReader.close();
}
}
/* (non-Javadoc)
* @see java.lang.Runnable#run()
*/
@Override
public synchronized void run()
{
while (listening)
{
String readStr = null;
try {
while((readStr=bufferedReader.readLine())!=null)
{
System.err.println("[Server]:"+readStr);
}
} catch (IOException e) {
listening = false;
if(socketStatusListener!=null)
{
int status = parseSocketStatus(e);
socketStatusListener.onSocketStatusChanged(socket, status, e);
}
e.printStackTrace();
return;//终止线程继续运行,这里也可以使用continue
}
}
}
private int parseSocketStatus(IOException e)
{
if(SocketException.class.isInstance(e))
{
String msg = e.getLocalizedMessage().trim();
if("Connection reset".equalsIgnoreCase(msg))
{
return SocketStatusListener.STATUS_RESET;
}
else if("Socket is closed".equalsIgnoreCase(msg))
{
return SocketStatusListener.STATUS_CLOSE;
}
else if("Broken pipe".equalsIgnoreCase(msg))
{
return SocketStatusListener.STATUS_PIP_BROKEN;
}
}
return SocketStatusListener.STATUS_UNKOWN;
}
/**
* listen:(这里用一句话描述这个方法的作用).
* TODO(这里描述这个方法适用条件 – 可选).
*
*/
public void startListener(SocketStatusListener ssl) {
listening = true;
this.socketStatusListener = ssl;
start();
}
}
写入任务
package com.io.sockets;
import java.io.BufferedWriter;
import java.io.IOException;
import java.io.OutputStreamWriter;
import java.net.Socket;
public class WriterTask extends Thread{
private BufferedWriter bufferedWriter;
private String msg = null;
private Socket socket = null;
public WriterTask(Socket socket) throws IOException {
this.bufferedWriter = new BufferedWriter(new OutputStreamWriter(socket.getOutputStream()));
this.socket = socket;
}
/**
* finishTask:(这里用一句话描述这个方法的作用).
* TODO(这里描述这个方法适用条件 – 可选).
* @throws IOException
*
*/
public void finish() throws IOException {
if(bufferedWriter!=null && socket!=null)
{
if(!socket.isOutputShutdown())
{
socket.shutdownOutput();
}
bufferedWriter.close();
}
}
/* (non-Javadoc)
* @see java.lang.Runnable#run()
*/
@Override
public synchronized void run() {
try {
bufferedWriter.write(msg);
bufferedWriter.flush();
} catch (IOException e) {
e.printStackTrace();
}
}
public void send(String msg){
this.msg = msg;
new Thread(this).start();
}
}
Server端测试
public class TcpSocketServer {
public static void main(String[] args) {
List serverHandlers = new CopyOnWriteArrayList();
ServerSocket serverSocket = null;
try {
serverSocket = new ServerSocket(8090, 5);
while(true)
{
Socket clientSocket = serverSocket.accept();
if(clientSocket.isConnected())
{
SocketHandler serverHandler = new SocketHandler(clientSocket);
serverHandlers.add(serverHandler);
serverHandler.listen(true);
serverHandler.sendMessage("Host:"+serverSocket.getInetAddress().getHostAddress()+"\r\n");
/*while (true)
{
Scanner sc = new Scanner(System.in);
String next = sc.nextLine()+"\r\n";
for (SocketHandler scItem : serverHandlers) {
scItem.sendMessage(next);
}
}*/
}
}
} catch (IOException e) {
e.printStackTrace();
}finally{
try {
for (SocketHandler serverHandler : serverHandlers)
{
serverHandler.shutDown();
}
serverHandlers.clear();
serverSocket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
客户端测试
public class TcpSocketClient {
public static void main(String[] args) {
SocketHandler clientHandler = null;
try {
Socket clientSocket = new Socket("localhost", 8090);
clientSocket.setKeepAlive(true);
clientSocket.setTcpNoDelay(true);
if(clientSocket.isConnected())
{
clientHandler = new SocketHandler(clientSocket);
clientHandler.listen(true);
while (true)
{
Scanner sc = new Scanner(System.in);
String next = sc.nextLine()+"\r\n";
if(!clientSocket.isClosed())
{
clientHandler.sendMessage(next);
}else{
break;
}
}
}
} catch (IOException e) {
e.printStackTrace();
}finally{
clientHandler.shutDown();
}
}
}
原文:http://my.oschina.net/ososchina/blog/509052
java 异步socket_java Socket读写异步分离相关推荐
- java 阻塞 socket_java socket非阻塞I/O
1 非阻塞(Nonblocking)体系结构 在这一部分,我将从理论的角度来解释非阻塞体系的结构及其工作原理.这部"喜剧"(当然,如果你喜欢的话也可以称做戏剧)的&quo ...
- boost::asio向socket中异步读写数据
内容代码参考自: Boost.Asio C++ Network Programming Cookbook 异步写入数据的核心是异步回调函数. 在此之前, 必须弄明白异步IO的基本概念和回调函数触发的时 ...
- Java 非阻塞 IO 和异步 IO
转载自 Java 非阻塞 IO 和异步 IO 上一篇文章介绍了 Java NIO 中 Buffer.Channel 和 Selector 的基本操作,主要是一些接口操作,比较简单. 本文将介绍非阻塞 ...
- JAVA Web Servlet中的异步处理 (2) -- Servlet3.1中的Non-blocking IO支持
JAVA Web Servlet中的异步处理 (2) – Servlet3.1中的Non-blocking IO支持 在servlet 3.1中,新增了non-blocking IO支持. 在serv ...
- java服务端异步处理机制_Java异步处理机制实例详解
通常同步意味着一个任务的某个处理过程会对多个线程在用串行化处理,而异步则意味着某个处理过程可以允许多个线程同时处理.下面我们就来看看有关异步处理的详细内容. 异步通常代表着更好的性能,因为它很大程度上 ...
- 同步Socket 与 异步 Socket
同步Socket 与 异步 Socket: 1.同步就是阻塞的,比如 接受数据 如果没有回应 就一直等待. 2.异步就是不用等待: 同步Socket using System; using Syste ...
- java登录时启动后台异步线程_JAVA多线程的同步和 异步
原标题:JAVA多线程的同步和 异步 1.多线程和异步操作的异同 多线程和异步操作两者都可以达到避免调用线程阻塞的目的,从而提高软件的可响应性.甚至有些时候我们就认为多线程和异步操作是等同的概念.但是 ...
- 通用异步 Windows Socket TCP 客户端组件的设计与实现
编写 Windows Socket TCP 客户端其实并不困难,Windows 提供了6种 I/O 通信模型供大家选择.但本座看过很多客户端程序都把 Socket 通信和业务逻辑混在一起,剪不断理还乱 ...
- 高并发 python socket send 异步_在Python中使用异步Socket编程性能测试
ok,首先写一个python socket的server段,对开放三个端口:10000,10001,10002.krondo的例子中是每个server绑定一个端口,测试的时候需要分别开3个shell, ...
最新文章
- 第十周项目实践1 二叉树算法验证
- 安装了超图、oracle、eclipse、JDK后系统的java进程情况以及java.exe、javaw.exe
- LeetCode-二分查找-69. Sqrt(x)
- 【Python 自然语言处理 第二版】读书笔记1:语言处理与Python
- What's VPC (by quqi99)
- 中国的电商发展迅速,有了取代实体的趋势
- abort has been called翻译_小分享:一款优秀的你还不知道的免费翻译工具推荐给大家...
- 明道云实现产品BOM清单的快速搭建
- hermite spline
- MediaRecorder MPEG4Writer
- 利用python进行正球面的大圆航程与横向线航程计算
- 京东秒杀技巧有哪些(京东秒杀技巧大全)
- css实现小气泡样式和模拟京东快递单号放大效果
- 电阻、电容和电感的选型及作用
- Hive汽车销售数据分析系统实战开发:
- 关于接口测试--面试题
- Shell脚本实现多选DNS同时批量解析域名IP地址(新更新)
- 百度云AI文字识别SDK在node中的使用
- 使用canvas截图跨域导致的报错(Failed to execute ‘toDataURL‘ on ‘HTMLCanvasElement)
- cmgr linux命令,gprs AT 指令
热门文章
- DPtoLP/LPtoDP 和 ScreenToClient/ClientToScreen
- 关于返回结构体的函数
- c#与java之比较(转自Jack.Wang's home)
- android wifi连接手机,Android手机无线连接利器-AirDroid
- 2018计算机河北省高考试题,2018年河北高考物理压轴试题【含答案】
- Android ViewPager指示器
- chromedriver : Saving to 安装卡住 解决
- idea中代码能够运行,但是显示类找不到
- vasp服务器中断,求助VASP能带计算的中断原因
- html 鼠标图标做成动画效果,纯css3实现的鼠标悬停动画按钮