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
相關文章
相關標籤/搜索