跨语言之间的socket通信(C--Java的握手)

http://blog.csdn.net/xuanner/archive/2008/01/07/2029022.aspx

 

作者:  xuanner  发布日期: 2008-1-7 17:15:01  Email:[email protected]

----------------------------------(原创作品,请保留作者著作信 息)--------------------------------------------

       这些日子在公司开发一个基于B/S的服务器监控的, 服务器端是视频电话系统,是C语言UDP的WinSock建立的Socket监听,客户端我是用了JSP进行开发,开发环境是 MyEclipse6.0+Tomcat5.5+jdk6.0,于是要用Java的UDP socket与WinSock进行握手谈话,嘻嘻,说得形象了点。首先开始谈话吧!!!!!!!!.................

(1) 谈话开始,先讲下一点网络知识吧。

xuanner老师:socket握手后,双方通信的是什么东西呢?
学生:就是字节。
xuanner老师:那是什么字节?主机字节 还是网络字节?
学生:网络字节。
xuanner老师:那解释下网络字节跟主机字节有什么区别?
学生:想了想说,就是高位在前跟在 后的区别了,网络字节是低位在前,高位在后的,而主机字节是高位在前,低位在后。比如说在C语言声明一个int类型的值,它是四个字节保存的,它的前两个 字节就是高位,后两个字节就是低位,有一种算法可以把它转为网络字节。(后面提供)
xuanner老师:好,不错!!那么 WinSock握手后发数据包时,Java Socket取得到后如何处理呢?
学生:得到数据包(字节数组)后,再把网络字节转为主机字节就可以 了,有一种算法可以把它转为主机字节。(后面提供)
xuanner老师:对,还挺聪明的。但如果WinSock握手后发送的数据包含有字符呢,或 是中文字符呢?该如何实现呢?
学生:想了又想,不知道怎么回答。回答不会。
xuanner老师:首先要了解C语言与Java语言数据类型 的数据编码与存储格式,C语言字符是以系统默认GBK为编码格式,而Java语言字符是以JVM为编码格式。WinSock发送数据包是字符以ANSI存 储格式发送的,到了Java Socket后,直接将其转换为String类型。
xuanner老师:那如果是Java Socket发送的数据包含有中文字符,如何打包?
学生:直接把String以GBK编码格式转换为bytes即可。

好啦,网络socket握手讲解完毕。

(2)数据类型编码算法
<1>Java 中int类型主机字节转换为网络字节算法[ 封包 ]

/**  
  * 将int转为低字节在前,高字节在后的byte数组
  
*/

 
//  封包int算法
private   static   byte [] InttoByteArray( int  n)  {
        
byte [] b  =   new   byte [ 4 ];
        b[
0 =  ( byte ) (n  &   0xff );
        b[
1 =  ( byte ) (n  >>   8   &   0xff );
        b[
2 =  ( byte ) (n  >>   16   &   0xff );
        b[
3 =  ( byte ) (n  >>   24   &   0xff );
        
return  b;
}

<2>Java中short类型主机字节转换为网络字节算法[ 封包 ]

/**
  * 将short转为低字节在前,高字节在后的byte数组(网络字节)
  
*/

// 封包short算法
private   static   byte [] ShorttoByteArray( short  n)  {
        
byte [] b  =   new   byte [ 2 ];
        b[
1 =  ( byte ) (n  &   0xff );
        b[
0 =  ( byte ) (n  >>   8   &   0xff );        
        
return  b;
}

<3>Java 中int类型网络字节转换为主机字节算法[ 解包 ]

//  解包为int算法
private   static   int  ByteArraytoInt( byte [] b)  {
        
int  iOutcome  =   0 ;
        
byte  bLoop;
        
for  ( int  i  =   0 ; i  <   4 ; i ++ {
                bLoop 
=  b[i];
                iOutcome 
+=  (bLoop  &   0xff <<  ( 8   *  i);
        }

        
return  iOutcome;
}

<4>Java 中short类型网络字节转换为主机字节算法[ 解包 ]

//  解包为short算法
privatestatic  short  ByteArraytoShort( byte [] b)  {
        
short  iOutcome  =   0 ;
        
byte  bLoop;
        
for  ( int  i  =   0 ; i  <   2 ; i ++ {
                bLoop 
=  b[i];
                iOutcome 
+=  (bLoop  &   0xff <<  ( 8   *  i);
        }

        
return  iOutcome;
}

<5>Java中ANSI字符数组转为String字符串[ 解包 ]
//  解包为String算法
private   static  String ByteArraytoString( byte [] b)  {
        
//  转化为Unicode编码格式
        String retStr  =   "" ;
        
try   {
                retStr 
=   new  String(b,  " GBK " );          //" GB2312"也可以
        }
  catch  (Exception e)  {
        }

        
return  retStr.trim();
}
<6>Java中String字符串转换为ANSI字符数组[ 封包 ]
public   byte [] StringtoByteArray(String str)  {
        
byte [] retBytes  =   null ;
        
try   {
                retBytes 
=  str.getBytes( " GBK " );         //" GB2312"也可以
        }
  catch (Exception ex)  {}
        
return  retBytes;
}

       总结:解决java的字符编码问题首先需要明确的是你的问题中涉及到哪些编码,当前默认编码(不一定是系统的,而是JVM的)是什么,然后才好利用各种解 决方法来解决。
希望我写这篇文章对你有帮助,My love CSDN 网友们。

                                                                                                                                                              csdn author: xuanner
                                                                                                                                                                          2008-1-7

 

你可能感兴趣的:(java,算法,socket,网络,语言,byte)