|
|
发表于 2014-2-27 06:43:15
|
显示全部楼层
哈哈,你例子是一个伪命题,你那个定义AA方法是不存在的。
只有可能是下面两种情况:
第一种:- char AA[6]={0x0a,0x0f,0x01,0x0e,0x06,0x0c};
复制代码 第二种:- char AA[6]={'a','f','1','e','6','c'};
复制代码 第一种:
移位就行了
- unsigned long CharArrayToNumber( unsigned char *p_pBuff, int p_iSize )
- {
- if( NULL != p_pBuff && p_iSize > 0 && p_iSize <= 8 )
- {
- unsigned long ulRet = 0;
- p_iSize -= 1;
- for(int i=0;i<=p_iSize;++i)
- {
- ulRet |= ((unsigned long)(p_pBuff[i]))<<((p_iSize-i)<<2);
- }
- return ulRet;
- }
- else
- {
- // arduino 有没有 throw 我不知道,异常肯定就挂了,怎么调试我也不知道
- //throw "CharArrayToNumber: arg error";
- return 0;
- }
- }
复制代码 你的例子就写成:
- char AA[6]={0x0a,0x0f,0x01,0x0e,0x06,0x0c};
- unsigned long ulVal = CharArrayToNumber(AA,6);
复制代码 第二种:
就比较麻烦了,需要一个字符到数字的转换,估计你想要这个的可能性大
- inline unsigned long CharToNumber( unsigned char p_ucVal )
- {
- switch(p_ucVal)
- {
- case '0':
- return 0;
- case '1':
- return 1;
- case '2':
- return 2;
- case '3':
- return 3;
- case '4':
- return 4;
- case '5':
- return 5;
- case '6':
- return 6;
- case '7':
- return 7;
- case '8':
- return 8;
- case '9':
- return 9;
- case 'A':
- return 10;
- case 'B':
- return 11;
- case 'C':
- return 12;
- case 'D':
- return 13;
- case 'E':
- return 14;
- case 'F':
- return 15;
- case 'a':
- return 10;
- case 'b':
- return 11;
- case 'c':
- return 12;
- case 'd':
- return 13;
- case 'e':
- return 14;
- case 'f':
- return 15;
- default:
- // arduino 有没有 throw 我不知道,异常肯定就挂了,怎么调试我也不知道
- //throw "CharToNumber: arg error";
- return 0;
- }
- }
复制代码 这么写为了速度快,当然为了好看可以把 A 和 a 写一起,但写一起编译器恐怕不能优化成跳转,AVR的汇编我不了解,哪位了解可以看一下反汇编确定一下。
如果不确定,又追求效率,可以自己优化,给个思路:
- inline unsigned long CharToNumber( unsigned char p_ucVal )
- { // 如果要用,具体 0 的数目对不对最好自己数清楚一下。。。
- static const unsigned char __TransferArray[] = {0,1,2,3,4,5,6,7,8,9,0,0,0,0,0,0,0,10,11,12,13,14,15,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,10,11,12,13,14,15};
- if( p_ucVal >= '0' && p_ucVal <= 'f' )
- { // 意思就是这一步在自己的代码里就保证了肯定是指针跳转
- return __TransferArray[p_ucVal-'0'];
- }
- else
- {
- //throw "CharToNumber: arg error";
- return 0;
- }
- }
- unsigned long CharArrayToNumber( unsigned char *p_pBuff, int p_iSize )
- {
- if( NULL != p_pBuff && p_iSize > 0 && p_iSize <= 8 )
- {
- unsigned long ulRet = 0;
- p_iSize -= 1;
- for(int i=0;i<=p_iSize;++i)
- {
- ulRet |= CharToNumber(p_pBuff[i])<<((p_iSize-i)<<2);
- }
- return ulRet;
- }
- else
- {
- //throw "CharArrayToNumber: arg error";
- return 0;
- }
- }
复制代码 你的例子就写成:
- char AA[6]={'a','f','1','e','6','c'};
- unsigned long ulVal = CharArrayToNumber(AA,6);
复制代码 =========================================================
ulVal 既是 0xAF1E6C 也是 11476588
- printf("ulVal=0x%X\n", ulVal);
- printf("ulVal=0x%ld\n", ulVal);
- // 输出:
- ulVal=0xAF1E6C
- ulVal=11476588
复制代码 不过你这个需求真的很奇怪,一个 char 的范围本身就是 0x00-0xFF 了
你那个AA为什么不是 char AA[4]={0x00,0xaf,0x1e,0x6c} ?
如果是大端系统就可以直接:
- unsigned long ulVal = *((unsigned long *)AA);
复制代码 小端系统0、3字节1、2字节交换后,就和上面一样直接强转。
大致就这么几种,根据你的情况用吧。总的来说 arduino 对性能的要求比较苛刻,
但效率主要取决于设计思路,具体代码的优化只能是毛毛雨。
arduino 是大端还是小端系统我还真没注意,测一下很简单:
- void TestEndian()
- {
- static union {
- char _c[4];
- unsigned long _l;
- } __endian_test = { 'l', '0' ,'0', 'b' };
- if( 'b' == ((char)__endian_test._l) )
- printf("是大端系统\n");
- else
- printf("是小端系统\n");
- }
复制代码 |
|