java 和 C++ Socket通讯(java做为服务端server,C++做为客户端client,解决中文乱码问题GBK和UTF8)

 

原文连接: http://www.cnblogs.com/kenkofox/archive/2010/04/25/1719649.htmlhtml

 

代码:java

http://files.cnblogs.com/kenkofox/Client-CPlusPlus.rar
http://files.cnblogs.com/kenkofox/Server_Java.rargit

 

java和C++使用Socket通讯,其实底层Socket都是相通的,因此只须要按照各自的语法去作就是了。github

 

java服务器端使用ServerSocket的accept建立Socket,跟普通java之间的通讯一致。数据库

C++客户端使用makeConnect(server, port, "tcp"),send,recv等函数。编程

 

本身在此次编程中,首先遇到的是虽然链接成功了,但java没法接收C++发来的消息。数组

多是用错函数之类的,后边改成下边的代码接收就没事了。服务器

 

1             //接受数据,但不容许有中文,由于会乱码
 2              DataInputStream in = new DataInputStream(clientSocket.getInputStream());
 3             byte[] buffer = new byte[10000];  //缓冲区的大小
 4              in.read(buffer);               //处理接收到的报文,转换成字符串
 5              /**
6              * C++传递过来的中文字,须要转化一下。C++默认使用GBK。
7              * GB2312是GBK的子集,只有简体中文。由于数据库用GB2312,因此这里直接转为GB2312
8              * */
 9             message = new String(buffer,"GB2312").trim();

 

 

另外socket

最大的问题是字符的编码问题,若是发现java接收到的字符串是乱码,就要仔细看看接下来的说明了。tcp

 

Java代码在运行时,默认用UTF8来处理字符串,Socket发送字符串(若是用高层输出流直接输出String的话,最后仍是自动用UTF8方式把字符串拆分红byte数组再传输的。(能够见http://www.cnblogs.com/kenkofox/archive/2010/04/23/1719009.html

而C++在xp运行的时候默认使用GBK来传输Socket。

 

因此java接收到C++消息的时候,应该转为GBK或者GB2312,才能显示正确中文。

而C++要接收到正确的java消息,就要在java发送的时候转为GBK或者GB2312编码(由于C++转码比java麻烦不少嘛,哈哈)

 

1    byte[] responseBuffer = newClientRequestHandler(message).response().getBytes("GB2312");
2    out.write(responseBuffer, 0,responseBuffer.length);

 

 

而C++接收方面,只须要用buf装起来,而后转为string就是了。正确显示……代码大概是:

charCount = recv(socket, buf, len, 0);

string resultString(buf);

 

另外为了更好理解上述的编码问题,你们在java端发送信息到C++端的时候,试试下边的方式试试,颇有意思的。记得要在C++那边关注charCount  

 

//得到输出输出流
out = newPrintStream(clientSocket.getOutputStream());
 out.print(test);//直接UTF8输出,最终底层每一个中文用3个字节传输
 out.print(newString(test.getBytes(),"GBK"));//转GBK失败,实际每一个中文字用了4到5个字节传递
 out.print(newString(test.getBytes("GBK"),"GBK"));//转GBK,但底层仍是要拆成字节数组,固然最终仍是跟UTF8同样

 

 

 

接下来是完整的代码说明

java方面:

EchoServerThread是一个Server类,专门等待客户的链接,而后创建EchoThread进行处理。

EchoThread是一个处理消息的线程,主要包括接收消息和发送消息的socket操做。

ClientRequestHandler是处理字符串的实际业务逻辑类……

 

C++方面:

client.cpp是测试的主函数。 

SocketManager.h包含SocketManager类,简单封装了Socket的启动和发送等操做。

connection.h包含Connection类,封装了Socket的底层调用。

conn_exception.h定义了一个异常。

 

 

kenkofox@qq.com https://github.com/kenkozheng
相关文章
相关标签/搜索