java和C#之间SOCKET通信的问题
转自:http://www.cdtarena.com/javapx/201307/9170.html
java和C#之间SOCKET通信的问题
一、服务器端(使用java编写)
/**
* 监听客户端的请求
*
*/
private static void socketService()
{
ExecutorService exec = Executors.newCachedThreadPool();
try
{
ServerSocket server=new ServerSocket(5678);
int i = 1;
while(true)
{
MyLogManager.InfoLog(log, null,"等待连接第"+i+"个用户...");
try
{
Socket client=server.accept();
MyLogManager.InfoLog(log, null,"第"+i+"个用户连接完成!");
exec.execute(new PDAServerWithDB(client));
}
catch(Exception whileExp)
{
String msg = "多线程处理连接失败!";
MyLogManager.ErrorLog(log, whileExp, msg);
}
i++;
}
}
catch(IOException ioe)
{
String msg = "连接失败!";
MyLogManager.ErrorLog(log, ioe, msg);
exec.shutdown();
}
}
具体对于Socket信息的接受和发送在PDAServerWithDB类中处理
信息处理分为:接收数据和发送数据
服务端接收数据一律采用ReadLine()方法,这就要求客户端在发送请求时要有行结束符。
服务器的接收发送数据的代码
a)构造输入输出流
InputStream inPut = s.getInputStream();
OutputStream outPut = s.getOutputStream();
PrintWriter outWriter=new PrintWriter(outPut);
BufferedReader inputReader =new BufferedReader(new InputStreamReader(inPut));
b)接收客户端请求的代码
String request = inputReader.readLine();
request = request.trim();
request = request.replaceAll("\n", "");
c)向客户端发送文本数据的代码
outWriter.println(strInfo);
outWriter.flush();
d)向客户端发送文件的代码
// 发送文件长度
File file = new File(filePath);
byte[] outBytes = new byte[1024];
int count = 0;
FileInputStream fileInput = new FileInputStream(file);
ByteArrayOutputStream ow = new ByteArrayOutputStream();
while ((count = fileInput.read(outBytes)) > 0) {
MyLogManager.DebugLog(log, null, String.valueOf(count));
ow.write(outBytes, 0, count);
}
outPut.write(ow.toByteArray());
//outWriter.print(ow);//这个在JAVA客户端时可以正常响应,而在C#客户端中无法响应。
//outWriter.flush();
二、客户端(使用java和c#两个版本)
1).发送请求信息(字符串格式)
对于JAVA来说:直接使用PrintWrite类的println()方法即可。
而对于C#来说:需要使用socket.Send(System.Text.Encoding.ASCII.GetBytes(msg + "\r"));需要在请求信息msg后面加上一个行结束标志符。http://www.cdtarena.com/php/
2).接收数据(文本或者文件)
2-1).java客户端接收数据
a)java接收文本的代码示例:
******代码示例*****
log.info("开始连接服务器");
InetAddress address = InetAddress.getByName(AppConfig.IP);//193.100.100.143);
SocketChannel sc = SocketChannel.open(new InetSocketAddress(address,AppConfig.PORT));
log.info("服务器连接成功");
//连接成功 初始化流
InputStream inputStream = Channels.newInputStream(sc);
InputStreamReader is = new InputStreamReader(inputStream,"GBK");
in = new BufferedReader(is);
log.info("接收服务器的数据");
String responseLine="";
while ((responseLine = in.readLine()) != null)
{
//用readLine接收数据是,会自动抛弃换行符,如果为了保持数据的格式,需要在这里加上一个换行标识符
returnStr += responseLine+"\n";
}
log.info("接收服务器的数据完毕");
**************
b)java接收文件的示例代码:
*****代码示例*****
log.info("开始连接服务器");
InetAddress address = InetAddress.getByName("193.100.100.159");//193.100.100.143);
SocketChannel sc = SocketChannel.open(new InetSocketAddress(address,AppConfig.PORT));
log.info("服务器连接成功,开始初始化流");
//连接成功 初始化流
OutputStream outputStream = Channels.newOutputStream(sc);
InputStream inputStream = Channels.newInputStream(sc);
InputStreamReader inputStreamReader = new InputStreamReader(inputStream);
byte[] b = new byte[1024];
ByteArrayOutputStream bArrStream = new ByteArrayOutputStream(fileLength);
int readCount = 0;
while ((readCount = inputStream.read(b)) != -1)
{
log.info(readCount);
bArrStream.write(b, 0, readCount);
}
log.info("size:"+bArrStream.toByteArray().length);
log.info("接收服务器的数据完毕");
**************
2-2.) c#客户端接收数据的代码
a)接收文本数据
*****代码示例*****
Socket socket = null;
MemoryStream memStream = null;
string returnMsg = string.Empty;
//与服务器建立连接
socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
IPAddress add = IPAddress.Parse(appConfig.Ip);
IPEndPoint endPt = new IPEndPoint(add, appConfig.Port);
socket.Connect(endPt);
//接收数据
byte[] buffer = new byte[1024];
int recCount = 0;
memStream = new MemoryStream();
//接收返回的字节流
while ((recCount = socket.Receive(buffer)) > 0)
{
memStream.Write(buffer, 0, recCount);
}
Encoding encoding = Encoding.GetEncoding("GBK");
returnMsg = encoding.GetString(memStream.GetBuffer(), 0, memStream.GetBuffer().Length);
**************
b)接收文件数据
****代码示例****
//接收数据
byte[] buffer = new byte[1024];
int recCount = 0;
MemoryStream memStream = new MemoryStream();
while ((recCount = socket.Receive(buffer)) > 0)
{
memStream.Write(buffer, 0, recCount);
}
//接下来按照文件格式,将memStream保存为文件即可
**************
=======以上是最终使用的代码版本===========
在开发过程中出现的问题及其解决
1.)文本乱码问题
java服务器端代码文件是使用GBK编码。所以在客户端读取的时候使用GBK编码进行转换。
2.)客户端和服务端的交互。
在服务端使用PrintWriter类来封装数据发送流(发送数据),new BufferedReader(new InputStreamReader(InputStream))来封装输入流(读取数据)
服务端读数据的时候是使用ReadLine方法,所以就要求客户端发送请求时需要有一个行结束标志。对于java来说是用println()即可,
而对于C#则需要在发送信息的后面手动增加一个行结束标识符"\r"。
对于服务端的反馈信息有两种反馈方式,一个是println(),一个是write(byte[])。前者是文本的发送,后者是文件的发送。
在使用print(object)方法对文件发送时,java客户端可是正确的接收数据,而C#客户端却不能,所以才采用了write(byte[])方法进行发送。
接收数据时,还要对按行发送的文本数据进行去尾处理
这个处理java和c#一样,只是方法名的大小写不同
str = str.trim();
str = str.replaceAll("\r", "");
str = str.replaceAll("\n", "");
java和C#之间SOCKET通信的问题的更多相关文章
- 我看不下去鸟。。。。Java和C#的socket通信真的简单吗?
这几天在博客园上看到好几个写Java和C#的socket通信的帖子.但是都为指出其中关键点. C# socket通信组件有很多,在vs 使用nuget搜索socket组件有很多类似的.本人使用的是自己 ...
- Android模拟器的ip获取以及模拟器之间socket通信
Android模拟器的ip获取以及模拟器之间socket通信 http://kalogen.iteye.com/blog/1565507 作者:李波 实现网络五子棋时用到了两个设备 ...
- Java和C#的socket通信相关(转)
这几天在博客园上看到好几个写Java和C#的socket通信的帖子.但是都为指出其中关键点. C# socket通信组件有很多,在vs 使用nuget搜索socket组件有很多类似的.本人使用的是自己 ...
- 关于Java和.NET之间的通信问题(JSON)
前言: 最近项目在某XX领导的所谓指引下,非要转型Java,转就转吧,在转的过程前期是个痛苦期,特别.NET旧有项目和Java新项目需要通信时. 进入主题,Java和.NET之间需要通信,这时媒介很多 ...
- Java进阶(四十七)Socket通信
Java进阶(四十七)Socket通信 今天讲解一个 Hello Word 级别的 Java Socket 通信的例子.具体通讯过程如下: 先启动Server端,进入一个死循环以便一直监听某端口是 ...
- Java网络编程和NIO详解1:JAVA 中原生的 socket 通信机制
Java网络编程和NIO详解1:JAVA 中原生的 socket 通信机制 JAVA 中原生的 socket 通信机制 摘要:本文属于原创,欢迎转载,转载请保留出处:https://github.co ...
- Java实现简单的socket通信
今天学习了一下java如何实现socket通信,感觉难点反而是在io上,因为java对socket封装已经很完善了. 今天代码花了整个晚上调试,主要原因是io的flush问题和命令行下如何运行具有pa ...
- Java线程——线程之间的通信
Java中多线程间的通信是怎么实现的? 线程通信的方式: (1)共享变量 线程之间的通信可以通过发送信号,发送信号的一个简单方法就是再共享的对象里面设置信号值.线程A在一个同步块中设置boolean型 ...
- Java 实现简单的 Socket 通信
Java socket 封装了传输层的实现细节,开发人员可以基于 socket 实现应用层.本文介绍了 Java socket 简单用法. 1. 传输层协议 传输层包含了两种协议,分别是 TCP (T ...
随机推荐
- 《Java4Android视频教程》学习笔记(二)
一:面向对象 1.对象 ①对象的使用方法 对象.变量 对象.方法 ②匿名对象 new A().方法 new A().变量 匿名对象会被分配到对内存中 java内存处理机制会对一定时间内无指针指向的对象 ...
- gravitas是什么意思_gravitas在线翻译_英语_读音_用法_例句_海词词典
gravitas是什么意思_gravitas在线翻译_英语_读音_用法_例句_海词词典 gravitas
- tocken和ticket的数据模型;
/* jshint -W079 */ /* jshint -W020 */ "use strict"; var _ = require("lodash"); m ...
- nginx 使用安装问题及解决方案
如何安装清参考:http://www.runoob.com/linux/nginx-install-setup.html 可以先不用配置,等理解后在配置. 在启动nginx时,出现提示: nginx: ...
- raphael入门到精通---入门篇之总览
什么是Raphael raphael.js是一小巧的javascript库,它可以在web上画矢量图简化你的工作,如果你想创建你指定的图表,图形区域或者可移动的组件,那么就使用raphael吧 话不多 ...
- C#获取时间的函数
//获取日期+时间DateTime.Now.ToString(); // 2012-9-4 20:02:10DateTime.Now.ToLocalTime().ToString ...
- 深入剖析哪些服务是Oracle 11g必须开启的
这篇文章主要介绍了哪些服务是Oracle 11g必须开启的以及这些服务的详细介绍,需要的朋友可以参考下 成功安装Oracle 11g数据库后,你会发现自己电脑运行速度会变慢,配置较低的电脑甚至出现 ...
- 从51跳新唐cortex学习3——细说新唐两种定时器
的定时器我们已经是相当熟悉啦.但是,对于第一次接触新唐,第一次接触cortex的定时器一样,都是加1计数,但是功能和容量变大了),包括4个32位定时器(里面放24位的数据),还有分频功能.TMER0到 ...
- MVC模式已死
MVC模式:Model模型 View试图 Control控制器,是目前主流模式,被当作服务器软件入门基本模式学习和掌握,主流框架Struts 1/2 JSF Wicket基本都顺理成章支持MVC模式. ...
- USACO 2001 OPEN
第1题 绿组. 奶牛接力赛[relay] 题目描述 农夫约翰已经为一次赛跑选出了K(2≤K≤40)头牛组成了一支接力队.赛跑在农夫约翰所拥有的农场上进行,农场的编号为1到Ⅳf4≤Ⅳ< 800), ...