如何解决Java Socket通信技术收发线程互斥
Java Socket通信技术在很长的`时间里都在使用,在不少的程序员眼中都有很多高的评价。那么下面我们就看看如何才能掌握这门复杂的编程语言,希望大家在今后的Java Socket通信技术使用中有所收获。
下面就是Java Socket通信技术在解决收发线程互斥的代码介绍。
age ;
rt ception;
rt tStream;
rt utStream;
rt SocketAddress;
rt et;
rt etException;
rt etTimeoutException;
rt leDateFormat;
rt ;
rt erties;
rt r;
rt rTask;
rt urrentHashMap;
rt Unit;
rt ition;
rt trantLock;
rt er;
19./**
20.*
title: socket通信包装类
21.*
Description:
22.*
CopyRight: CopyRight (c) 2009
23.*
Company:
24.*
Create date: 2009-10-14
25.*author sunnylocus
26. * v0.10 2009-10-14 初类
27.* v0.11 2009-11-12 对命令收发逻辑及收发线程互斥机制进行了优化,
处理命令速度由原来8~16个/秒提高到25~32个/秒
28.*/ public class SocketConnection {
ate volatile Socket socket;
ate int timeout = 1000*10; //超时时间,初始值10秒
ate boolean isLaunchHeartcheck = false;//是否已启动心跳检测
ate boolean isNetworkConnect = false; //网络是否已连接
ate static String host = "";
ate static int port;
ic InputStream inStream = null;
ic OutputStream outStream = null;
ate static Logger log =ogger
(s);
ate static SocketConnection socketConnection = null;
ate static r heartTimer=null;
40.//private final Map
synchronizedMap(new HashMap
ate final ConcurrentHashMap
= new ConcurrentHashMap
ate static Thread receiveThread = null;
ate final ReentrantLock lock = new ReentrantLock();
ate SocketConnection(){
erties conf = new Properties();
{
(esourceAsStream
(""));
out = eOf(roperty("timeout"));
(roperty("ip"),eOf
(roperty("port")));
50.} catch(IOException e) {
l("socket初始化异常!",e);
w new RuntimeException("socket初始化异常,请检查配置参数");
53.}
54.}
55./**
56.* 单态模式
57.*/
ic static SocketConnection getInstance() {
(socketConnection==null) {
hronized(s) {
(socketConnection==null) {
etConnection = new SocketConnection();
rn socketConnection;
64.}
65.}
66.}
rn socketConnection;
68.}
ate void init(String host,int port) throws IOException {
SocketAddress addr = new InetSocketAddress(host,port);
et = new Socket();
hronized (this) {
("【准备与"+addr+"建立连接】");
ect(addr, timeout);
("【与"+addr+"连接已建立】");
ream = nputStream();
tream = utputStream();
cpNoDelay(true);//数据不作缓冲,立即发送
oLinger(true, 0);//socket关闭时,立即释放资源
eepAlive(true);
rafficClass(0x04|0x10);//高可靠性和最小延迟传输
tworkConnect=true;
iveThread = new Thread(new ReceiveWorker());
t();
=host;
=port;
(!isLaunchHeartcheck)
chHeartcheck();
89.}
90.}
91./**
92.* 心跳包检测
93.*/
ate void launchHeartcheck() {
(socket == null)
w new IllegalStateException("socket is not
established!");
tTimer = new Timer();
unchHeartcheck = true;
dule(new TimerTask() {
ic void run() {
ng msgStreamNo = treamNo("kq");
mstType =9999;//999-心跳包请求
leDateFormat dateformate = new SimpleDateFormat
("yyyyMMddHHmmss");
ng msgDateTime = at(new Date());
msgLength =38;//消息头长度
ng commandstr = "00" +msgLength + mstType + msgStreamNo;
("心跳检测包 -> IVR "+commandstr);
reconnCounter = 1;
e(true) {
ng responseMsg =null;
{
onseMsg = readReqMsg(commandstr);
113.} catch (IOException e) {
r("IO流异常",e);
nnCounter ++;
116.}
(responseMsg!=null) {
("心跳响应包 <- IVR "+responseMsg);
nnCounter = 1;
k;
121.} else {
nnCounter ++;
123.}
(reconnCounter >3) {//重连次数已达三次,判定网络连接中断,
重新建立连接。连接未被建立时不释放锁
nnectToCTCC(); break;
126.}
127.}
128.}
129.},1000 * 60*1,1000*60*2);
130.}
131./**
132.* 重连与目标IP建立重连
133.*/
ate void reConnectToCTCC() {
Thread(new Runnable(){
ic void run(){
("重新建立与"+host+":"+port+"的连接");
138.//清理工作,中断计时器,中断接收线程,恢复初始变量
el();
unchHeartcheck=false;
tworkConnect = false;
rrupt();
{
e();
145.} catch (IOException e1) {r("重连时,关闭socket连
接发生IO流异常",e1);}
146.//----------------
hronized(this){
(; ;){
{
entThread();
p(1000 * 1);
(host,port);
fyAll();
k ;
155.} catch (IOException e) {
r("重新建立连接未成功",e);
157.} catch (InterruptedException e){
r("重连线程中断",e);
159.}
160.}
161.}
162.}
163.})t();
164.}
165./**
166.* 发送命令并接受响应
167.* @param requestMsg
168.* @return
169.* @throws SocketTimeoutException
170.* @throws IOException
171.*/
ic String readReqMsg(String requestMsg) throws IOException {
(requestMsg ==null) {
rn null;
175.}
(!isNetworkConnect) {
hronized(this){
{
(1000*5); //等待5秒,如果网络还没有恢复,抛出IO流异常
(!isNetworkConnect) {
w new IOException("网络连接中断!");
182.}
183.} catch (InterruptedException e) {
r("发送线程中断",e);
185.}
186.}
187.}
ng msgNo = tring(8, 8 + 24);//读取流水号
tream = utputStream();
e(ytes());
h();
ition msglock = ondition(); //消息锁
193.//注册等待接收消息
(msgNo, msglock);
{
();
t(timeout,ISECONDS);
198.} catch (InterruptedException e) {
r("发送线程中断",e);
200.} finally {
ck();
202.}
ct respMsg = ve(msgNo); //响应信息
(respMsg!=null &&(respMsg != msglock)) {
205.//已经接收到消息,注销等待,成功返回消息
rn (String) respMsg;
207.} else {
r(msgNo+" 超时,未收到响应消息");
w new SocketTimeoutException(msgNo+" 超时,未收到响应消息");
210.}
211.}
ic void finalize() {
(socket != null) {
{
e();
216.} catch (IOException e) {
tStackTrace();
218.}
219.}
220.}
221.//消息接收线程
ate class ReceiveWorker implements Runnable {
ng intStr= null;
ic void run() {
e(!rrupted()){
{
[] headBytes = new byte[4];
((headBytes)==-1){
("读到流未尾,对方已关闭流!");
nnectToCTCC();//读到流未尾,对方已关闭流
rn;
232.}
[] tmp =new byte[4];
= headBytes;
ng tempStr = new String(tmp)();
(tempStr==null || ls("")) {
r("received message is null");
inue;
239.}
tr = new String(tmp);
totalLength =eInt(intStr);
242.//----------------
[] msgBytes = new byte[totalLength-4];
(msgBytes);
ng resultMsg = new String(headBytes)+ new
String(msgBytes);
246.//抽出消息ID
ng msgNo = tring(8, 8 + 24);
ition msglock =(Condition) (msgNo);
(msglock ==null) {
(msgNo+"序号可能已被注销!响应消息丢弃");
ve(msgNo);
inue;
253.}
(msgNo, resultMsg);
{
();
alAll();
258.}finally {
ck();
260.}
261.}catch(SocketException e){
r("服务端关闭socket",e);
nnectToCTCC();
264.} catch(IOException e) {
r("接收线程读取响应数据时发生IO流异常",e);
266.} catch(NumberFormatException e){
r("收到没良心包,String转int异常,异常字符:"+intStr);
268.}
269.}
270.}
271.}
272.}
相關文章
-
Java如何通过Socket实现TCP服务端
Socket 通常也称作套接字,Java如何通过Socket实现TCP服务端?下面本站小编带大家一起来看看详细内容,希望对大家有所帮助!想了解更多相关信息请持续关注我们应届毕业生考试网! 1 Java Socket简介所谓socket 通常也称作 -
java与javascript之间json格式数据互转详解
javascript中对象与字符串的互转对象转为字符串:通过de方法,这个是里面的方法,引入到当前文件就可以了。字符串转换为对象:①使用de方法,同上,引入js就可以了。②jQuery中有个方法,$eJson也可以实现。java中json字符串与对象 -
java如何利用java.net.URLConnection发送HTTP请求
如何通过Java发送HTTP请求,通俗点讲,如何通过Java(模拟浏览器)发送HTTP请求。下面是由本站小编为大家整理的java如何利用onnection发送HTTP请求,喜欢的可以收藏一下!了解更多详情资讯,请关注应届毕业生考试网! 运用原生Jav -
Javascript实例教程如何使用HoTMetal
HoTMetal中使用javascript3.什么样的资源适合于脚本编写当利用HotMetal PRO 6.0编写宏的时候,你可以使用以下几种资源:预定义事件HoTMetaL PRO 6.0定义了几个事件以及特殊的用户定义的宏来处理它们。这些宏应该根基HoTM -
Java中基于Aspectwerkz的AOP开发
一、AOP编程概览面向对象编程技术进入软件开发的主流对软件的开发方式产生了极大的影响,开发者可以用一组实体以及这些实体之间的关系将系统形象地表示出来,这使得他们能够设计出规模更大、更复杂的系统,开发周期也比以 -
如何运用Java socket实现多人聊天室功能
导语:如何运用Java socket实现多人聊天室功能呢?下面是小编给大家提供的代码实现,大家可以参考阅读,更多详情请关注应届毕业生考试网。目录结构: ChatClient: package ;import .*;import t.*;import .*;import .*;@ -
javasocket服务端技巧
Java的主要工作是通过编程语言来制作互联网页面、制作动态效果以及网站等技术,以下是小编为大家搜索整理的`javasocket服务端技巧,欢迎阅读!更多精彩内容请及时关注我们应届毕业生考试网!如下的GreetingServer 程序是一 -
Java中Websocket使用实例解析
在 WebSocket API,浏览器和服务器只需要要做一个握手的动作,然后,浏览器和服务器之间就形成了一条快速通道。两者之间就直接可以数据互相传送。下面小编给大家介绍Java中Websocket使用实例解析,欢迎阅读! Java中Websoc -
SUN认证考试知识点:Java Socket通信读取相关信息代码
Java Socket通信读取有不少需要我们注意的知识点。当我们在使用的时候有很多的`问题摆在我们面前。下面我们就来详细的学习有关Java Socket通信读取的相关代码编写。以下是Java Socket通信读取的相关代码。rt eredRea -
如何解决AutoCAD转Protel99se丢线问题
工作中经常需要将AutoCAD里面的图形导入到Protel99SE,导入的过程中碰到的最大的问题就是:导入后的图形丢失了曲线(圆弧)。下面给大家分享解决办法。 AutoCAD版本:AutoCAD 2004 Chs1、用AutoCAD打开dwg文件,另存为AutoC