对dsPIC系列单片机C语言编程中乘除法计算的编程感悟

         个人使用单片机有些时间了,尤其是在这个快速变化的时代,数字编程已经是工科生必备的素养了。

         虽然说单片机现在也支持C语言编程了,但是和计算机的C语言编程也存在一些差异,尤其是在进行数据乘除法计算的时候。

         有些单片机不一定使用的标准C语言编译器,请注意不同单片机的编程风格,具体请

         单片机从以前的汇编,逐渐支持C语言编译器,但是可能支持部分C语言,不一定是标准的C语言编译器。


        以dsPIC单片机为例,以下有两种C语言除法编程风格:

uint16_t  a;
uint16_t  temp;
uint16_t  b;

//example 1: 标准C语言编译器的除法

    b  =  (a << 10)/1023;

//example 2: dsPIC 单片机支持的乘法与除法
temp = __builtin_muluu(a,1024); b = __builtini_divud(temp,1023);

      上面两种写法,第一种计算结果是正确的,只有第二种写法在dsPIC单片机上才能得到正常的结果。

      根本的原因在于编译器对整形乘除数据,处理方式不一样。

      以下有两种C语言乘法编程风格:

uint16_t    a;
uint16_t    b;
long    c;
long    d;

a = 32676;
b = 32676;
//example 1: 标准C语言的无符号整数乘法 c = a * b; //example 2: dsPIC内部自带的无符号整数乘法 d = __builtin_muluu(a,b);

uint16_t    a;
uint16_t    b;
long    c;
long    d;

a = 256;
b = 256;

//example 3:  标准C语言的无符号整数乘法

       c   =  a * b;

//example 4: dsPIC内部自带的无符号整数乘法

       d   =  __builtin_muluu(a,b);

      上面两种写法,第一种计算的结果是错误的,第二种计算的结果是正确的。

      原因是dsPIC单片机没有合适的工作寄存器来存储a*b的值。所以计算结果不同。

      当a*b的值小于65535时,两种计算方式的计算结果都是正确的。

uint16_t    a;
uint16_t    b;
long    c;
long    d;

a = 100;
b = 100;

//example 5:  标准C语言的无符号整数乘法

       c   =  a * b;

//example 6: dsPIC内部自带的无符号整数乘法

       d   =  __builtin_muluu(a,b);

uint16_t    a;
uint16_t    b;
long    c;
long    d;

a = 256;
b = 255;

//example 7:  标准C语言的无符号整数乘法

       c   =  a * b;

//example 8: dsPIC内部自带的无符号整数乘法

       d   =  __builtin_muluu(a,b);

      C语言编译器的不同,对于a*b结果的中间工作寄存器不同,导致标准C语言的写法在单片机上不能正确的编译。


      为了以后的工作中少走弯路,学弟学妹们,

      请优先学习该单片机的官方的参考文档;

      请优先使用内部自带的函数;

      请优先学习官方IDE的Help文档;  

原文地址:https://www.cnblogs.com/cjyc/p/15541891.html