C++编写二进制字符数组转ASCII码的函数
来源:互联网 发布:大巴车出租软件 编辑:程序博客网 时间:2024/05/30 02:22
原文链接:http://blog.csdn.net/gzliudan/article/details/23478169
在工控通信中经常用到16进制和ASCII码字符数组互相转换的功能,虽然功能简单,但初学者写出来的代码经常会有各种问题。从16进制转为ASCII吗的功能函数,一个比较简洁的实现版本如下:
void HexToAscii( char * Dest, char * Src, int SrcLen )
{
for ( int i = 0, j = 0; i < SrcLen; i++ )
{
char HiHalf = Src[i] >> 4;
char LoHalf = Src[i] & 0x0F;
Dest[j++] = ( HiHalf <= 9 ) ? ( HiHalf + '0' ) : ( HiHalf - 10 + 'A' );
Dest[j++] = ( LoHalf <= 9 ) ? ( LoHalf + '0' ) : ( LoHalf - 10 + 'A' );
}
}
在以上短短几行代码里,基础比较扎实的同学比较容易发现的一个Bug是用signed char来处理二进制数据,这样当被处理的字节Src[i]是负数时就会出现错误的转换结果。同样把HiHalf和LoHalf声明为int,也是有相同Bug的。解决办法是先把Src[i]转为unsigned char,并且把HiHalf和LoHalf定义为unsigned char。
一个比较隐蔽的严重问题是当Dest和Src字符数组有重叠的地址空间时,转换结果也会不对。例如Dest和Src的地址相等时,Src[0]转换为Dest[0]和Dest[1]后,Src[1]被Dest[1]覆盖,Src[1]还没转换里面的数据已经不是原来的数据了,依次类推。
除此以外,传进来的指针Dest和Src都要先判断是否等于NULL,这样才能尽量保证写出安全的代码。
最后一点,最好把Dest和Src声明为void *类型的指针,这样对非char类型的数据调用此函数时,就不需要强制转化。
修正后的代码如下:
void HexToAscii( void * DestBuf, void * SrcBuf, int SrcLen )
{
if ( ( DestBuf == NULL ) || ( SrcBuf == NULL ) )
{
return;
}
unsigned char * Dest = (unsigned char *) DestBuf;
unsigned char * Src = (unsigned char *) SrcBuf;
int DestPos = SrcLen << 1;
int SrcPos = SrcLen;
while ( --SrcPos >= 0 )
{
unsigned char HiHalf = Src[SrcPos] >> 4;
unsigned char LoHalf = Src[SrcPos] & 0x0F;
Dest[--DestPos] = ( HiHalf <= 9 ) ? ( HiHalf + '0' ) : ( HiHalf + 55 );
Dest[--DestPos] = ( LoHalf <= 9 ) ? ( LoHalf + '0' ) : ( LoHalf + 55 );
}
}
有兴趣的同学可以写个单元测试验证一下转化结果。或者改用查表法来转化,省去一些计算步骤。
- C++编写二进制字符数组转ASCII码的函数
- 用C++编写16进制字符数组转ASCII码字符数组的函数
- 【C#】字符转ASCII码,ASCII码转字符
- 【C#】字符转ASCII码,ASCII码转字符
- 【C#】字符转ASCII码,ASCII码转字符
- 【C#】字符转ASCII码,ASCII码转字符
- [C#][轉]字符转ASCII码,ASCII码转字符
- 17. 编写函数,将字符串中下标为奇数的字符按ASCII码升序排列
- 请编写函数fun,对长度位7个字符的字符串,除首尾字符外,将其余5个字符按ascii码降序排列
- C语言字符与ASCII码的互转,字符和整型的转换
- 字符的ASCII码
- C语言基础 ASCII转换成二进制存入数组中
- 字符转ASCII码
- ascii码转字符
- JS中字符问题(二进制/十进制/十六进制及ASCII码之间的转换)
- JS中字符问题(二进制/十进制/十六进制及ASCII码之间的转换)
- JS中字符问题(二进制/十进制/十六进制及ASCII码之间的转换)
- 如何由二进制ASCII码(010101)得到相应的字符
- Linux学习之CentOS(二十五)--Linux磁盘管理:LVM逻辑卷基本概念及LVM的工作原理
- 单片机的led跑马灯程序
- 暴力枚举-POJ2965 The Pilots Brothers' refrigerator
- 用C++实现ASCII码字符数组转16进制字符数组的功能
- http://os.51cto.com/art/201005/202380.htm
- C++编写二进制字符数组转ASCII码的函数
- Co-training&主动学习
- IIS中网站匿名访问权限问题解决办法
- uva 1315 - Crazy tea party(数论)
- VirtualBox 共享文件夹设置 及 开机自动挂载
- web开发常识积累
- poj2386Lake Counting(DFS算法)
- test
- 【玩转cocos2d-x之二十三】多线程和同步03-图片异步加载