单片机/MCU论坛
直播中

PKZz

7年用户 25经验值
私信 关注
[问答]

求大佬指教单片机16位数据的BCD码转换

就是这种这种8位的十六进制数temp(0~255)
百位 bai=temp/100;
temp=temp%100;//取余数
shi=temp/10;
ge=temp%10;

16位的也是一样,只是先除以1000(不太懂后面的)

回帖(17)

勇哥-lzu

2018-5-4 10:09:16
引用: PKZz 发表于 2018-5-5 16:56
#include"reg52.h"
#include "intrins.h"

speed变量改成了int,void write_fsm2(uchar add,uchar dat)也要改成void write_fsm2(uchar add,uint dat),write_fsm1也一样要改
举报

longrenwenzi

2018-5-4 16:47:43
问题描述的详细一点,不知道你在问什么呢。
举报

PKZz

2018-5-4 23:13:54
引用: longrenwenzi 发表于 2018-5-4 16:47
问题描述的详细一点,不知道你在问什么呢。


uint speed=50;
void write_fsm1(uchar add,uchar date)
{
        uchar qian,bai,shi,ge;
        qian=date/1000;
        bai=date%1000/100;
        shi=date%1000%100/10;
        ge=date%1000%100%10;
        write_ml(0x80+add);
        write_data(0x30+qian);
        write_data(0x30+bai);
        write_data(0x30+shi);
        write_data(0x30+ge);}
write_fsm1(6,speed);
大概程序就这样写的,但是输入数据大于255就显示不出来是什么原因呢?求指教
举报

武林

2018-5-5 08:23:22
引用: PKZz 发表于 2018-5-4 23:13
uint speed=50;
void write_fsm1(uchar add,uchar date)
{

void write_fsm1(uchar add,uchar date)的入口参数的数据类型要改为unsigned int
举报

人中狼

2018-5-5 09:10:29
计算时最好能包括万位,除非确定数据在千位以内
举报

PKZz

2018-5-5 10:41:03
引用: wulinwl 发表于 2018-5-5 08:23
void write_fsm1(uchar add,uchar date)的入口参数的数据类型要改为unsigned int

改成了unsigned long int 还是在只能显示小与255的数,请问是不是51单片机只能计算8位的原因?16位数据是不是要分成2部分来计算?
举报

PKZz

2018-5-5 10:43:29
引用: 人中狼 发表于 2018-5-5 09:10
计算时最好能包括万位,除非确定数据在千位以内

是的,只用到千位,主要是51单片机计算16位数据要分成两部分吗?
举报

李增科

2018-5-5 13:44:28
引用: PKZz 发表于 2018-5-5 10:41
改成了unsigned long int 还是在只能显示小与255的数,请问是不是51单片机只能计算8位的原因?16位数据是不是要分成2部分来计算?

51单片机RAM是8位,因此计算的数据限于8位2进制数,最大的8位2进制数即255,要想计算出更大的数据就要区分高位和低位,对于16位数据,分为高8位和低8位,在程序编写时要将高8位和低8位分别存在两个寄存器中计算。最大的16位的2进制数是2的17次方减一,可以容易的表示千位甚至万位的10进制数。
举报

勇哥-lzu

2018-5-5 16:05:52
引用: PKZz 发表于 2018-5-5 10:41
改成了unsigned long int 还是在只能显示小与255的数,请问是不是51单片机只能计算8位的原因?16位数据是不是要分成2部分来计算?

显示不出来还是显示的不正确,比如256显示为0,这是显示不正确,应为uchar 最大是255;如果是这样,将uchar 改成unsigned short或者int就可以了;如果是没有数字或者乱码就很奇怪了

51单片机虽然是8位的,但是可以处理16位的short和32位int数据,不需要进行特别的处理;这些编译器会做的
举报

PKZz

2018-5-5 16:49:42
引用: 勇哥-lzu 发表于 2018-5-5 16:05
显示不出来还是显示的不正确,比如256显示为0,这是显示不正确,应为uchar 最大是255;如果是这样,将uchar 改成unsigned short或者int就可以了;如果是没有数字或者乱码就很奇怪了

51单片机虽然是8位的,但是可以处理16位的short和32位int数据,不需要进行特别的处理;这些编译器会做的 ...

输入大于255的数,显示的是减去256的数,定义改成unsigned int也没变化
举报

勇哥-lzu

2018-5-5 16:51:50
引用: PKZz 发表于 2018-5-5 16:49
输入大于255的数,显示的是减去256的数,定义改成unsigned int也没变化

把你改后的代码贴一下
举报

PKZz

2018-5-5 16:56:23
引用: 勇哥-lzu 发表于 2018-5-5 16:51
把你改后的代码贴一下

#include"reg52.h"
#include "intrins.h"

/*******************ºê¶¨Òå**************************************************/
#define uchar unsigned char
#define uint unsigned int //ºê¶¨Òå
//#define P0_value 0x3f
/*******************¶Ë¿Ú¶¨Òå¼°¿ª±ÙÏàÓ¦µÄ´æ´¢µ¥Ôª***************************/

***it lcd_ce=P2^2; //ʹÄܶË
***it lcd_rs=P2^0; //Êý¾Ý/ÃüÁîÑ¡Ôñ¶Ë
***it lcd_rw=P2^1; //¶Á/дѡÔñ¶Ë

***it LedT=P2^3;//Í£Ö¹µÆ
***it LedZ=P2^4;//ÕýתµÆ
***it LedF=P2^5;//·´×ªµÆ

***it PWM=P3^7;
***it IN_Z=P3^0;
***it IN_F=P3^1;

uchar code table1[]="SPEED:0000 r/min";                //×Ö·û´®ÏÔʾÊý×é
uchar code table2[]="S E T:0000 r/min";
unsigned int speed =0;
unsigned int speed_s=50;
char pwm=30;

uchar aa,bb,cc;                //±£´æµ±Ç°¶¨Ê±Æ÷µÄÖµ
uchar key=16;uchar buff;

void chushihua(); //ÉêÃ÷³õʼ»¯×Óº¯Êý
void delay(uint z); //ÉêÃ÷ÑÓʱº¯Êý
void write_ml(uchar m); //ÉêÃ÷дÃüÁî×Óº¯Êý
void write_data(uchar s); //ÉêÃ÷дÊý¾Ý×Óº¯Êý
void write_fsm1(uchar add,uchar date);
void write_fsm2(uchar add,uchar dat);
void motor();

void key_scan(void)//°´¼üɨÃè³ÌÐò
{
        uchar hang,lie;
        P1=0xf0;
        if((P1&0xf0)!=0xf0)
        {
                delay(1);
                if((P1&0xf0)!=0xf0)
                {
                        hang=0xfe;
                        while((hang&0x10)!=0)
                        {
                                P1=hang;
                                if((P1&0xf0)!=0xf0)
                                {
                                        lie=(P1&0xf0)|0x0f;
                                        buff=((~hang)+(~lie));
                                        switch(buff)
                                        {
                                                case 0x81:key=0;break;
                                                case 0x41:key=1;break;
                                                case 0x21:key=2;break;
                                                case 0x11:key=3;break;
                                                case 0x82:key=4;break;
                                                case 0x42:key=5;break;
                                                case 0x22:key=6;break;
                                                case 0x12:key=7;break;
                                                case 0x84:key=8;break;
                                                case 0x44:key=9;break;
                                                case 0x24:key=10;break;
                                                case 0x14:key=11;;break;
                                                case 0x88:key=12;break;
                                                case 0x48:key=13;break;
                                                case 0x28:key=14;break;
                                                case 0x18:key=15;break;
                                        }
                                }
                                else hang=(hang<<1)|0x01;
                        }
                }
        }
}
void anjian()
{
        key_scan();
        if (key==0)
        {speed_s=70;
        }
        if (key==1)
        {speed_s=80;
        }
        if (key==2)
        {speed_s=90;
        }
        if (key==3)
        {TR0=1;TR1=1;IN_Z=1;IN_F=0;LedF=1;LedZ=0;LedT=1;//Õýת
        }
        if (key==4)
        {speed_s=40;
        }
        if (key==5)
        {speed_s=50;
        }
        if (key==6)
        {speed_s=60;
        }
        if (key==7)
        {TR0=1;TR1=1;IN_Z=0;IN_F=1;LedF=0;LedZ=1;LedT=1;//·´×ª
        }
        if (key==8)
        {speed_s=10;
        }
        if (key==9)
        {speed_s=20;
        }
        if (key==10)
        {speed_s=30;
        }
        if (key==11)
        {if (speed_s<=0){speed_s=0;}else speed_s--;
        }
        if (key==12)
        {TR0=0;IN_Z=0;IN_F=0;speed_s=0;LedF=1;LedZ=1;LedT=0;//Í£Ö¹
        }
        if (key==13)
        {speed_s=100;
        }
        if (key==14)
        {speed_s=110;
        }
        if (key==15)
        {if (speed_s>=160){speed_s=160;}else speed_s++;
        }
        key=16;

}
void timer0() interrupt 1
{
        TH0 =(65536 - 100)/256;//100us³õÖµ
        TL0 =(65536 - 100)%256;
        aa++;
        if(aa>=100){
                aa=0;
                bb++;
        }
        if(bb>=45){
                speed=TH1*256+TL1;
                speed=speed*5;
                TH1=0;
                TL1=0;
                bb=0;
                cc++;
        }
        if(cc>=5)//200ms
  {motor();
        cc=0;
  }
        if(aa<=pwm) //pwm£¬¸ßµçƽÂö³åʱ¼ä
        {
                PWM=1;
                }
        else//µÍµçƽʱ¼ä
                PWM=0;
}
void motor()
{
        if(speed_s>speed){if(pwm<100){pwm++;}}
        if(speed_s0){pwm--;}}
}
void chushihua() //³õʼ»¯×Óº¯Êý
{
        uchar num;
        TMOD=0x51; //¶¨Ê±Æ÷0ÉèΪ¹¤×÷·½Ê½1
        TH0 =(65536 - 100)/256;
        TL0 =(65536 - 100)%256;
        TH1 = 0xfe;
        TL1 = 0xfe;
        EA=1; //¿ª×ÜÖжÏ
        ET0=1; //¿ª¶¨Ê±Æ÷0ÖжÏ
        TR0=0; //¶¨Ê±Æ÷0¹Ø±Õ
        ET1=1;        //¼ÆÊýÆ÷
        TR1=1;        //¼ÆÊýÆ÷
        IN_Z=0;
        IN_F=0;
        LedF=1;
        LedZ=1;
        LedT=0;
        PWM=0;
        lcd_ce=0;
        lcd_rw=0;
        write_ml(0x38); //ÏÔʾģʽÉèÖÃ
        write_ml(0x0c); //ÏÔʾ¿ª¹Ø¼°¹â±êÉèÖÃ
        write_ml(0x06); //µØÖ·¼Ó1ÕûÆÁ²»Òƶ¯
        write_ml(0x01); //ÇåÁã
       
        write_ml(0x80+0x00);
        for(num=0;num<16;num++)
        {
                write_data(table1[num]);
                delay(5);
        }
        write_ml(0x80+0x40);
        for(num=0;num<16;num++)
        {write_data(table2[num]);delay(5);}
}

void write_fsm1(uchar add,uchar date)//ÏÔʾÊýÖµµÚÒ»ÐÐ
{
        uchar qian,bai,shi,ge;
        qian=date/1000;
        bai=date%1000/100;
        shi=date%1000%100/10;
        ge=date%1000%100%10;
        write_ml(0x80+add);
        write_data(0x30+qian);
        write_data(0x30+bai);
        write_data(0x30+shi);
        write_data(0x30+ge);
}
void write_fsm2(uchar add,uchar dat)
{uchar qian,bai,shi,ge;
        qian=dat/1000;
        bai=dat%1000/100;
        shi=dat%1000%100/10;
        ge=dat%1000%100%10;
        write_ml(0x80+0x40+add);
        write_data(0x30+qian);
        write_data(0x30+bai);
        write_data(0x30+shi);
        write_data(0x30+ge);}

void write_ml(uchar m)
{
        lcd_rs=0;
        P0=m;
        delay(5);
        lcd_ce=1;
        delay(5);
        lcd_ce=0;
}

void write_data(uchar s)
{
        lcd_rs=1;
        P0=s;
        delay(5);
        lcd_ce=1;
        delay(5);
        lcd_ce=0;
}

void delay(uint z) //ÑÓʱ×Óº¯Êý
{
        uint x,y;
        for(x=z;x>0;x--)
        for(y=110;y>0;y--); //´óÔ¼1ºÁÃë
}


void main()
{
        chushihua();
        IN_Z=0;
        while(1)
        {
                anjian();
                motor();
                write_fsm1(6,speed);
                write_fsm2(6,speed_s);
        }
}
举报

PKZz

2018-5-5 16:59:43
引用: PKZz 发表于 2018-5-5 16:56
#include"reg52.h"
#include "intrins.h"

这是整个程序的代码,就是设置speed_s和测得的speed显示大于255就变成减去256的数
举报

人中狼

2018-5-5 17:03:16
用C语言编程的话不需要考虑数据需要几个字节,需要注意数据类型的定义,定义为char,是一个字节,定义为int,是两个字节。
四楼说的正确,void write_fsm1(uchar add,uchar date)里的date要定义为uint,不然其他类型的数据会强制转换为uchar,就只有一个字节了
举报

PKZz

2018-5-5 17:08:27
引用: 勇哥-lzu 发表于 2018-5-4 10:09
speed变量改成了int,void write_fsm2(uchar add,uchar dat)也要改成void write_fsm2(uchar add,uint dat),write_fsm1也一样要改

真的太感谢了,终于能正常显示了,一直看着speed的定义改了好久都没发现
举报

PKZz

2018-5-5 17:12:25
引用: 人中狼 发表于 2018-5-5 17:03
用C语言编程的话不需要考虑数据需要几个字节,需要注意数据类型的定义,定义为char,是一个字节,定义为int,是两个字节。
四楼说的正确,void write_fsm1(uchar add,uchar date)里的date要定义为uint,不然其他类型的数据会强制转换为uchar,就只有一个字节了 ...

学习了,一直没注意上面的定义有问题
举报

alonggege

2019-7-12 12:48:24
不错  学习了 谢谢
举报

更多回帖

发帖
×
20
完善资料,
赚取积分