float向u8和s8的转换

本文探讨了将浮点数(float)转换为整型数据(u8,s8等)时可能出现的问题,特别是当采用__ftol2_sse指令进行转换时的情况。文章通过具体的汇编代码示例展示了这一过程,并指出在转换过程中不会自动进行边界限制(clamp)。

关于float向u8,s8这种类型转换,比较内藏玄机,还是小心为妙,这种级别的优化做了不如不做。

直接float向char类型的做法是用__ftol2_sse命令完成,具体怎么做的就不跟了,想跟也能跟,结果放在al里面,然后move byte到结果。

这里是如果是范围相当,float是char能表示的数结果是正确的,如果是更大的,就是从4个byte中截取一个byte,不会有自动的clamp到边界-128这种。

到了针对unsigned char的表示可以看出使用频繁的loat,store完成的,本身就很慢,尽管c++代码很简洁,但是出来的汇编并不好,结果是截取类的,也是不会clamp。

 

 


 

 

    float a = -10.0f;

004132FE  fld         dword ptr [__real@c1200000 (415850h)] 

00413304  fstp        dword ptr [a] 

    char b = static_cast<char>(a);

00413307  fld         dword ptr [a] 

0041330A  call        @ILT+220(__ftol2_sse) (4110E1h) 

0041330F  mov         byte ptr [b],al 

    unsigned char c = (unsigned char)a;

00413312  fld         dword ptr [a] 

00413315  fnstcw      word ptr [ebp-0E6h] 

0041331B  movzx       eax,word ptr [ebp-0E6h] 

00413322  or          eax,0C00h 

00413327  mov         dword ptr [ebp-0ECh],eax 

0041332D  fldcw       word ptr [ebp-0ECh] 

00413333  fistp       dword ptr [ebp-0F0h] 

00413339  fldcw       word ptr [ebp-0E6h] 

0041333F  mov         al,byte ptr [ebp-0F0h] 

00413345  mov         byte ptr [c],al 


parallel studio自带intel 的指令集的文档,很不错

 

#include <reg52.h> #include <intrins.h> #define uchar unsigned char #define uint unsigned int typedef unsigned char U8; /* defined for unsigned 8-bits integer variable Ϟػۅ8λֻэҤ */ typedef signed char S8; /* defined for signed 8-bits integer variable Ԑػۅ8λֻэҤ */ typedef unsigned int U16; /* defined for unsigned 16-bits integer variable Ϟػۅ16λֻэҤ */ typedef signed int S16; /* defined for signed 16-bits integer variable Ԑػۅ16λֻэҤ */ typedef unsigned long U32; /* defined for unsigned 32-bits integer variable Ϟػۅ32λֻэҤ */ typedef signed long S32; /* defined for signed 32-bits integer variable Ԑػۅ32λֻэҤ */ typedef float F32; /* single precision floating point variable (32bits) եޫ׈ء֣˽è32λӤ׈é */ typedef double F64; /* double precision floating point variable (64bits) ˫ޫ׈ء֣˽è64λӤ׈é */ uchar code table[16]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90,0x88,0x83,0xc6,0xa1,0x86,0x8e};//ٲҴ˽ëڜҠë int temperature, humidity; //дݼքӽޅ sbit k1=P3^4; sbit k2=P3^5; sbit k3=P3^6; sbit k4=P3^7; //˽ëڜքλѡ sbit S1=P2^0; sbit S2=P2^1; sbit S3=P2^2; sbit S4=P2^3; //DHT11ӽޅ sbit DATA = P1^7; U8 U8FLAG,k; U8 U8count,U8temp; U8 U8T_data_H,U8T_data_L,U8RH_data_H,U8RH_data_L,U8checkdata; U8 U8T_data_H_temp,U8T_data_L_temp,U8RH_data_H_temp,U8RH_data_L_temp,U8checkdata_temp; U8 U8comdata; U8 count, count_r=0; U8 Read_Time=0; //ׁȡքʱݤ U8 SET_Time=10; //ʨ֨քʱݤĬɏˇ10 U8 set_flag=0; void Delay1(U16 j) { U8 i; for(;j>0;j--) { for(i=0;i<27;i++); } } void Delay_10us(void) { U8 i; i--; i--; i--; i--; i--; i--; } void COM(void) { U8 i; for(i=0;i<8;i++) { U8FLAG=2; while((!DATA)&&U8FLAG++); Delay_10us(); Delay_10us(); Delay_10us(); U8temp=0; if(DATA)U8temp=1; U8FLAG=2; while((DATA)&&U8FLAG++); //Ӭʱղ͸Զforѭ۷ if(U8FLAG==1)break; //Ɛ׏˽ߝλˇ0۹ˇ1 // ɧڻٟ֧ƽٟڽԤ֨0ٟ֧ƽֵղ˽ߝλΪ 1 U8comdata<<=1; U8comdata|=U8temp; //0 }//rof } //-------------------------------- //-----ςʪ׈ׁȡؓԌѲ ------------ //-------------------------------- //----ӔЂҤ߹ΪȫߖҤ-------- //----ς׈ٟ8λ== U8T_data_H------ //----ς׈֍8λ== U8T_data_L------ //----ʪ׈ٟ8λ== U8RH_data_H----- //----ʪ׈֍8λ== U8RH_data_L----- //----Уҩ 8λ == U8checkdata----- //----ַԃРژؓԌѲɧЂ---------- //---- Delay();, Delay_10us();,COM(); //-------------------------------- U8 RH(void) { //׷ܺ-֍18ms DATA=0; Delay1(200); //ԭ4Ϊ5 DATA=1; //؜Пԉʏ-֧ب-ٟ ׷ܺғʱ20us Delay_10us(); Delay_10us(); Delay_10us(); Delay_10us(); //׷ܺʨΪˤɫ Ɛ׏ՓܺЬӦхۅ DATA=1; //Ɛ׏ՓܺˇرԐ֍֧ƽЬӦхۅ ɧһЬӦղ͸ԶìЬӦղвЂՋѐ if(!DATA) //T ! { U8FLAG=2; //Ɛ׏ՓܺˇرעԶ 80us ք֍֧ƽЬӦхۅˇرޡ˸ while((!DATA)&&U8FLAG++); U8FLAG=2; //Ɛ׏ՓܺˇرעԶ 80us քٟ֧ƽìɧעԶղ޸ɫ˽ߝޓ˕״̬ while((DATA)&&U8FLAG++); //˽ߝޓ˕״̬ COM(); U8RH_data_H_temp=U8comdata; COM(); U8RH_data_L_temp=U8comdata; COM(); U8T_data_H_temp=U8comdata; COM(); U8T_data_L_temp=U8comdata; COM(); U8checkdata_temp=U8comdata; DATA=1; //˽ߝУҩ U8temp=(U8T_data_H_temp+U8T_data_L_temp+U8RH_data_H_temp+U8RH_data_L_temp); if(U8temp==U8checkdata_temp) { U8RH_data_H=U8RH_data_H_temp; U8RH_data_L=U8RH_data_L_temp; U8T_data_H=U8T_data_H_temp; U8T_data_L=U8T_data_L_temp; U8checkdata=U8checkdata_temp; }//fi return 1; }//fi else //ԫِǷһЬӦ { return 0; } } /*ғʱԌѲú*/ void delay(int n) { unsigned int i,j; for(i=0;i<n;i++) { for(j=0;j<121;j++); } } uchar Get_Key() { static bit flag=0; uchar k=0; if((flag==0)&&((k1==0)||(k2==0)||(k3==0)||(k4==0))) { delay(100); flag=1; if(k1==0){k=1;} else if(k2==0){k=2;} else if(k3==0){k=3;} else if(k4==0){k=4;} } else if((k1==1)&&(k2==1)&&(k3==1)&&(k4==1)){flag=0;} return k; } void Get_TH() { uint temp; temp = RH(); //ׁԶςʪ׈ìֻȡֻ˽ҿؖ humidity = U8RH_data_H; temperature = U8T_data_H; } //ˢт˽ëڜДʾ void Dispaly_data(uchar num1,uchar num2,uchar mode) { static uchar t=0; static uint m=0; if(mode==1)//ʁ˸ģʽ { if(++m<1000) { P0=0Xff; //ژҕДʾ return; } else if(m>2000) { m=0; } } P0=0xff; //ژҕДʾ switch(t) { case 0: S1=1;S2=0;S3=0;S4=0; P0=table[num1/10]; t++; break; case 1: S1=0;S2=1;S3=0;S4=0; P0=table[num1%10]; t++; break; case 2: S1=0;S2=0;S3=1;S4=0; P0=table[num2/10]; t++; break; case 3: S1=0;S2=0;S3=0;S4=1; P0=table[num2%10]; t=0; break; } } //֨ʱǷԵʼۯ void Init_Time() { //Եʼۯ֨ʱǷ50ms TMOD=0X01; TH0=(65536-50000)/256; TL0=(65536-50000)%256; EA=1; ET0=1; TR0=1; } /*׷ԌѲú*/ void main() { uchar key_num=0; Init_Time(); //Եʼۯ֨ʱǷ Get_TH(); //˗ЈׁһՎςʪ׈ while (1) { if(Read_Time>=SET_Time)//ׁȡʱݤֈԚʨ֨ʱݤ { Read_Time=0; Get_TH(); } key_num=Get_Key(); if(key_num==1) //ʨ׃дݼ { set_flag=1; } else if(key_num==2)//նݓдݼ { if(set_flag==1) { if(SET_Time<99)SET_Time++; } } else if(key_num==3)//ݵʙдݼ { if(set_flag==1) { if(SET_Time>1)SET_Time--; } } else if(key_num==4)//ȷ֨дݼ { set_flag=0; } if(set_flag==0)//ֽӣģʽДʾςʪ׈ { Dispaly_data(temperature,humidity,0); //Дʾςʪ׈ } else//ʨ֨ģʽДʾʱݤ { Dispaly_data(0,SET_Time,1); } } } //֨ʱא׏ؓԌѲ void time0(void) interrupt 1 using 1 { static uchar temp_time=0; TH0=(65536-50000)/256; TL0=(65536-50000)%256; if(set_flag==0)//ֽӣģʽ { if(++temp_time>=20)//1s { temp_time=0; Read_Time++; //ÿ1sݓ1 } } else//ʨ֨ģʽ { temp_time=0; } } 这段代码原本芯片是AT89C51现在要更改成STC15W4K32S4请重新编写代码
最新发布
12-17
评论 6
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值