找回密碼
 立即注冊(cè)

QQ登錄

只需一步,快速開始

帖子
查看: 12628|回復(fù): 37
收起左側(cè)

編寫的一個(gè)8個(gè)數(shù)碼管顯示的數(shù)字時(shí)鐘 但不能正常運(yùn)行 求大神幫忙看看

[復(fù)制鏈接]
ID:125657 發(fā)表于 2016-6-7 15:17 | 顯示全部樓層 |閱讀模式
編寫的一個(gè)8個(gè)數(shù)碼管顯示的數(shù)字時(shí)鐘可調(diào)鬧鐘  但不能正常運(yùn)行   程序還沒(méi)編完��!  
#include<reg51.h>
sbit KEY1=P1^0;
sbit KEY2=P1^1;
sbit KEY3=P1^2;
sbit LED=P2^2;
code unsigned char tab[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f};
unsigned char StrTab[8];
unsigned char minute=19,hour=23,second;
void delay(unsigned int cnt)
{
    while(--cnt);
}
void displaypro(void)
{
    StrTab[0]=tab[hour/10];
    StrTab[1]=tab[hour%10];  
    StrTab[2]=0x40;  
    StrTab[3]=tab[minute/10];  
    StrTab[4]=tab[minute%10];  
    StrTab[5]=0x40;  
    StrTab[6]=tab[second/10];  
    StrTab[7]=tab[second%10];  
}
main()
{
    TMOD=0x01;  //定時(shí)器0 10ms
    TH0=0xd8; //初始值
    TL0=0xf0;
    ET0=1;
    TR0=1;
    TMOD=0x10; //定時(shí)器1 動(dòng)態(tài)掃描
    TH1=0xf8;
    TL1=0xf0;
    ET1=1;
    TR1=1;
    EA=1;
    displaypro();
    while(1)
    {
    if(!KEY3)
        {
delay(10000);
if(!KEY3)
        {
          hour++;
          if(hour==24)
          hour=0;
          displaypro();
        }
        }
     if(!KEY2)
    {
    delay(10000);
    if(!KEY2)
      {
      minute++;
        if(minute==60)
   minute=0;
   displaypro();
       }
     }
        if(!KEY1)
    {
    delay(10000);
    if(!KEY1)
      {
      second++;
        if(second==60)
   second=0;
   displaypro();

   }
}
}
}
//定時(shí)器1中斷//
void time1_isr(void)interrupt 3 using 0
{
    static unsigned char num;
    TH1=0xf8;
    TL1=0xf0;
      switch(num)
      {
        case 0:P3=0xfe;P0=StrTab[num];break;
     case 1:P3=0xfd;P0=StrTab[num];break;
     case 2:P3=0xfb;P0=StrTab[num];break;
     case 3:P3=0xf7;P0=StrTab[num];break;
     case 4:P3=0xef;P0=StrTab[num];break;
     case 5:P3=0xdf;P0=StrTab[num];break;
     case 6:P3=0xbf;P0=StrTab[num];break;
     case 7:P3=0x7f;P0=StrTab[num];break;
     default:break;
      }
      num++;
      if(num==8)
          num=0;
}
//定時(shí)器0//
void time(void)interrupt 1 using 1
{
  static unsigned char count;
  TH0=0xd8;
  TL0=0xf0;
  count++;
  switch(count)
  {
    case 0:
    case 20:
    case 40:
    case 60:
    case 80:displaypro();break;
    case 50:P1=~P1;break;   //半秒 LED 閃爍
    default:break;
  }
  if(count==100)
  {
    count=0;
    second++;
    if(second==60)
      {
      second=0;
      minute++;
      if(minute==60)
        {
minute=0;
hour++;
if(hour==24)
   hour=0;
     }
      }
   }
}

相關(guān)帖子

回復(fù)

使用道具 舉報(bào)

ID:125657 發(fā)表于 2016-6-7 15:25 來(lái)自觸屏版 | 顯示全部樓層
正常顯示是12-12-12這樣  但是運(yùn)行后確實(shí)這樣顯示
UC_Photo_001.jpg
回復(fù)

使用道具 舉報(bào)

ID:125657 發(fā)表于 2016-6-7 15:25 來(lái)自觸屏版 | 顯示全部樓層
而且也不能正常計(jì)時(shí)
回復(fù)

使用道具 舉報(bào)

ID:123289 發(fā)表于 2016-6-7 16:56 | 顯示全部樓層
圖不清楚
回復(fù)

使用道具 舉報(bào)

ID:123289 發(fā)表于 2016-6-7 16:57 | 顯示全部樓層
寫程序習(xí)慣不好,沒(méi)有注釋。
回復(fù)

使用道具 舉報(bào)

ID:123289 發(fā)表于 2016-6-7 17:40 | 顯示全部樓層
1、取8個(gè)RAM單元(編號(hào)X0至X7)對(duì)應(yīng)存放8個(gè)LED的顯示內(nèi)容(譯碼后的LED段顯示值)。
2、取一個(gè)單元做計(jì)數(shù)器K,從0至7循環(huán)計(jì)數(shù),分別對(duì)應(yīng)指示顯示8個(gè)LED。
3、時(shí)間中斷只用一個(gè),考慮到8個(gè)LED掃描顯示,中斷時(shí)常數(shù)取5ms,中斷后做下列事件:
3.1、處理一下計(jì)數(shù)器(屏上顯示的數(shù)字,如時(shí)間年月日時(shí)分秒,或計(jì)數(shù)值等)……
3.2、先關(guān)所有LED顯示,防止切換閃動(dòng);
3.3、將K+1(注:當(dāng)K=8時(shí)清K=0。),將K所指示的Xn(當(dāng)然需要將對(duì)應(yīng)需要顯示的時(shí)鐘位,譯成LED碼后再送入Xn)送入顯示數(shù)據(jù)口,再打開K所指定的LED。
要點(diǎn):每次中斷只顯示一個(gè)LED,且先關(guān)后顯示。
回復(fù)

使用道具 舉報(bào)

ID:125692 發(fā)表于 2016-6-7 17:55 | 顯示全部樓層
重點(diǎn)需要強(qiáng)調(diào)出來(lái), 別人能夠很容易看懂
回復(fù)

使用道具 舉報(bào)

ID:125657 發(fā)表于 2016-6-8 08:12 來(lái)自觸屏版 | 顯示全部樓層
yzwzfyz 發(fā)表于 2016-6-7 17:40
1、取8個(gè)RAM單元(編號(hào)X0至X7)對(duì)應(yīng)存放8個(gè)LED的顯示內(nèi)容(譯碼后的LED段顯示值)。
2、取一個(gè)單元做計(jì)數(shù) ...

能不能幫我修改下程序   看哪里錯(cuò)了  
回復(fù)

使用道具 舉報(bào)

ID:123289 發(fā)表于 2016-6-8 10:03 | 顯示全部樓層
先將各行的注釋加上去,讓別人知道你的目的,再看你錯(cuò)在哪里。
也許:當(dāng)你完成注釋時(shí),自己就已經(jīng)明白了。
回復(fù)

使用道具 舉報(bào)

ID:123289 發(fā)表于 2016-6-8 10:14 | 顯示全部樓層
要點(diǎn):每次中斷只顯示一個(gè)LED,且先關(guān)后顯示�。。�
回復(fù)

使用道具 舉報(bào)

ID:123289 發(fā)表于 2016-6-8 10:50 | 顯示全部樓層
     case 0:P3=0xfe;P0=StrTab[num];break;
     case 1:P3=0xfd;P0=StrTab[num];break;
     case 2:P3=0xfb;P0=StrTab[num];break;
     case 3:P3=0xf7;P0=StrTab[num];break;
     case 4:P3=0xef;P0=StrTab[num];break;
     case 5:P3=0xdf;P0=StrTab[num];break;
     case 6:P3=0xbf;P0=StrTab[num];break;
     case 7:P3=0x7f;P0=StrTab[num];break;
這是T1中斷所做的事,雖然每次切換了LED,但顯示的內(nèi)容卻是相同的StrTab[num],這就必須保證,在每次中斷之前,StrTab[num]已被刷新,僅改變num是不夠的,因?yàn)轱@示的不是num,而是StrTab[num]!
如果某一次中斷前未刷新,則輪顯示的LED必定是上一輪的LED值,如此就混淆了。
你用兩個(gè)時(shí)間中斷的目的是什么?能保證正確地刷新LED數(shù)據(jù)么?
回復(fù)

使用道具 舉報(bào)

ID:125657 發(fā)表于 2016-6-8 15:20 | 顯示全部樓層
#include<reg51.h>
sbit KEY1=P1^0;        //定義端口參數(shù)
sbit KEY2=P1^1;
sbit KEY3=P1^2;
sbit LED=P2^2;        //定義指示燈

code unsigned char tab[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f};  //共陰極數(shù)碼管0-9
unsigned char StrTab[8]; //定義緩沖區(qū)
unsigned char minute=19,hour=23,second;        //定義初始化

void delay(unsigned int cnt)
{
    while(--cnt);
}

void displaypro(void)
{
    StrTab[0]=tab[hour/10];         //顯示小時(shí)
    StrTab[1]=tab[hour%10];  
    StrTab[2]=0x40;                   //顯示-
    StrTab[3]=tab[minute/10];  //顯示分鐘
    StrTab[4]=tab[minute%10];  
    StrTab[5]=0x40;                          //顯示-
    StrTab[6]=tab[second/10];          //顯示秒
    StrTab[7]=tab[second%10];  
}
main()
{
    TMOD |=0x01;  //定時(shí)器0 10ms 用于計(jì)時(shí)
    TH0=0xd8;        //初始值
    TL0=0xf0;
    ET0=1;
    TR0=1;

    TMOD |=0x10;        //定時(shí)器1 動(dòng)態(tài)掃描
    TH1=0xf8;
    TL1=0xf0;
    ET1=1;
    TR1=1;
    EA=1;
    displaypro();  //調(diào)用顯示處理函數(shù)

    while(1)
    {
    if(!KEY3)
        {
        delay(10000);
        if(!KEY3)          //按鍵3去抖以及動(dòng)作
               {
                 hour++;
                 if(hour==24)
                 hour=0;
                 displaypro();
               }
        }

     if(!KEY2)           //按鍵2去抖以及動(dòng)作
    {
    delay(10000);
    if(!KEY2)
      {
      minute++;
        if(minute==60)
          minute=0;
          displaypro();
       }
     }

               if(!KEY1)
    {
    delay(10000);
    if(!KEY1)           //按鍵1去抖以及動(dòng)作
      {
      second++;
        if(second==60)
          second=0;
          displaypro();


   }
}
}
}

//定時(shí)器1中斷//
void time1_isr(void)interrupt 3 using 0          //定時(shí)器1動(dòng)態(tài)掃描
{
    static unsigned char num;
    TH1=0xf8;
    TL1=0xf0;
      switch(num)

      {
        case 0:P3=0xfe;P0=StrTab[num];break;  //分別調(diào)用緩沖區(qū)的值進(jìn)行掃描
            case 1:P3=0xfd;P0=StrTab[num];break;
            case 2:P3=0xfb;P0=StrTab[num];break;
            case 3:P3=0xf7;P0=StrTab[num];break;
            case 4:P3=0xef;P0=StrTab[num];break;
            case 5:P3=0xdf;P0=StrTab[num];break;
            case 6:P3=0xbf;P0=StrTab[num];break;
            case 7:P3=0x7f;P0=StrTab[num];break;
            default:break;
      }

      num++;           //掃描8次,使用8個(gè)數(shù)碼管
      if(num==8)
          num=0;
}

//定時(shí)器0//
void time(void)interrupt 1 using 1
{
  static unsigned char count;  //定義內(nèi)部局部變量
  TH0=0xd8;
  TL0=0xf0;
  count++;
  switch(count)
  {
    case 0:
    case 20:
    case 40:
    case 60:
    case 80:displaypro();break;                 //隔一定時(shí)間調(diào)用顯示處理顯示處理
    case 50:P1=~P1;break;          //半秒 LED 閃爍
    default:break;
  }
  if(count==100)
  {
    count=0;
    second++;
    if(second==60)
      {
      second=0;
      minute++;
      if(minute==60)
        {
        minute=0;
        hour++;
        if(hour==24)
          hour=0;
            }
      }
   }
}

     
回復(fù)

使用道具 舉報(bào)

ID:125657 發(fā)表于 2016-6-8 15:22 | 顯示全部樓層

電路

電路



回復(fù)

使用道具 舉報(bào)

ID:125657 發(fā)表于 2016-6-8 15:25 | 顯示全部樓層
yzwzfyz 發(fā)表于 2016-6-8 10:50
case 0:P3=0xfe;P0=StrTab[num];break;
     case 1:P3=0xfd;P0=StrTab[num];break;
     case 2:P3 ...

我上傳了標(biāo)注的程序和電路圖了      他上面不是定義了    StrTab[0]=tab[hour/10];
    StrTab[1]=tab[hour%10];  
    StrTab[2]=0x40;  
    StrTab[3]=tab[minute/10];  
    StrTab[4]=tab[minute%10];  
    StrTab[5]=0x40;  
    StrTab[6]=tab[second/10];  
    StrTab[7]=tab[second%10];  

改變NUM就好了     
回復(fù)

使用道具 舉報(bào)

ID:125657 發(fā)表于 2016-6-8 15:35 | 顯示全部樓層
linlin2222 發(fā)表于 2016-6-7 17:55
重點(diǎn)需要強(qiáng)調(diào)出來(lái), 別人能夠很容易看懂

已經(jīng)標(biāo)注了  大神幫我看看吧
回復(fù)

使用道具 舉報(bào)

ID:111634 發(fā)表于 2016-6-8 19:09 | 顯示全部樓層
參考一下樓上的5種電子鐘電路、程序和仿真
回復(fù)

使用道具 舉報(bào)

ID:111634 發(fā)表于 2016-6-8 19:09 | 顯示全部樓層
樓上的5種電子鐘摘自張志良編著《單片機(jī)實(shí)驗(yàn)實(shí)訓(xùn)100例》 ISBN 978-7-5124-1603-1,北航社出版
回復(fù)

使用道具 舉報(bào)

ID:111634 發(fā)表于 2016-6-8 19:11 | 顯示全部樓層
讀懂了別人正確有效的電路和程序,才能找出自己電路和程序的錯(cuò)誤。
回復(fù)

使用道具 舉報(bào)

ID:111634 發(fā)表于 2016-6-8 19:12 | 顯示全部樓層
張志良編著《單片機(jī)實(shí)驗(yàn)實(shí)訓(xùn)100例》每個(gè)案例程序均有詳細(xì)分析,每條語(yǔ)句均有注釋。
回復(fù)

使用道具 舉報(bào)

ID:111634 發(fā)表于 2016-6-8 19:15 | 顯示全部樓層
你的程序沒(méi)有定義標(biāo)記和注釋,別人需花多少時(shí)間才能讀懂理順,然后再幫你尋找錯(cuò)誤,可能嗎?
回復(fù)

使用道具 舉報(bào)

ID:111634 發(fā)表于 2016-6-8 19:17 | 顯示全部樓層
先Proteus仿真一下

模擬電子鐘.jpg


以上摘自張志良編著《單片機(jī)實(shí)驗(yàn)實(shí)訓(xùn)100例》 ISBN 978-7-5124-1603-1,北航社出版
回復(fù)

使用道具 舉報(bào)

ID:123289 發(fā)表于 2016-6-9 11:40 | 顯示全部樓層
上圖的設(shè)計(jì)不是很好的:缺點(diǎn)如下:
1、用了6個(gè)(U2-U7),不經(jīng)濟(jì)。
改進(jìn),用一個(gè)晶體管陣列(一個(gè)IC里集成有7個(gè)三極管),驅(qū)動(dòng)LED的陽(yáng)極(共陽(yáng))。
2、LED的選擇驅(qū)動(dòng)用了P1,P3兩個(gè)口,不利于程序編寫。
改進(jìn),只用P1口驅(qū)動(dòng),這里軟件編寫方便許多。
3、四個(gè)發(fā)光二極管,兩兩串并,一般紅色壓降為1.4V,兩只2.8V,未經(jīng)限流直接接到IO口,使得2.2V電壓(5V-2.8V)加在CPU的芯片上,CPU發(fā)熱大。
改進(jìn):設(shè)LED是10mA一只。兩組并為20mA,串入一只電阻[R=(5V-2.8V-0.3V)/20=100歐,0.3V是IO口的壓降]。
回復(fù)

使用道具 舉報(bào)

ID:123289 發(fā)表于 2016-6-9 11:44 | 顯示全部樓層
寫書的人不一定認(rèn)真。
U2-U7驅(qū)動(dòng)的LED 7個(gè)段,都未限流,都是錯(cuò)誤的做法。
回復(fù)

使用道具 舉報(bào)

ID:111634 發(fā)表于 2016-6-9 17:50 | 顯示全部樓層
有人與我討論電路,很高興,首先表示感謝,并希望能交個(gè)朋友。有關(guān)問(wèn)題我的看法如下:
回復(fù)

使用道具 舉報(bào)

ID:111634 發(fā)表于 2016-6-9 17:50 | 顯示全部樓層
本電路設(shè)計(jì)為靜態(tài)顯示,雖然用了6片595,但595價(jià)格低廉。用595的好處是串行傳送,節(jié)省了I/O端口。
回復(fù)

使用道具 舉報(bào)

ID:111634 發(fā)表于 2016-6-9 17:51 | 顯示全部樓層
若用動(dòng)態(tài)顯示,7段加6位位控,需13根I/O端口線。因?yàn)椴慌懦S喽丝诰€還需其他用途。
回復(fù)

使用道具 舉報(bào)

ID:111634 發(fā)表于 2016-6-9 17:51 | 顯示全部樓層
本帖最后由 zl2168 于 2016-6-9 18:00 編輯

用6片595的另一好處是,便于修正時(shí)鐘參數(shù)。而且修正位是快速閃爍(每秒亮暗各5次),修正期間時(shí)鐘繼續(xù)正常運(yùn)行 。你Proteus仿真一下,試試效果。
回復(fù)

使用道具 舉報(bào)

ID:111634 發(fā)表于 2016-6-9 17:52 | 顯示全部樓層
本帖最后由 zl2168 于 2016-6-9 17:58 編輯

"驅(qū)動(dòng)用了P1,P3兩個(gè)口,不利于程序編寫",完全沒(méi)有這個(gè)問(wèn)題,看你程序怎么編寫。P3口是串行傳送數(shù)據(jù),P1口是位控加修正位快速閃爍。
回復(fù)

使用道具 舉報(bào)

ID:111634 發(fā)表于 2016-6-9 17:53 | 顯示全部樓層
至于沒(méi)有限流電阻,那是為了電路圖面簡(jiǎn)潔,連晶振和復(fù)位電路都沒(méi)畫。
回復(fù)

使用道具 舉報(bào)

ID:111634 發(fā)表于 2016-6-9 17:53 | 顯示全部樓層
實(shí)際電路應(yīng)該加限流電阻,不過(guò)無(wú)論是595、還是80C51,實(shí)際流不出很大電流的,長(zhǎng)期工作也不會(huì)使芯片過(guò)熱。
回復(fù)

使用道具 舉報(bào)

ID:111634 發(fā)表于 2016-6-9 17:55 | 顯示全部樓層
若僅僅是6位時(shí)鐘,沒(méi)有修正及修正位快速閃爍功能,電路可簡(jiǎn)單的多。
回復(fù)

使用道具 舉報(bào)

ID:111634 發(fā)表于 2016-6-9 18:03 | 顯示全部樓層
時(shí)鐘動(dòng)態(tài)顯示電路,并保留時(shí)鐘修正及修正位快速閃爍功能,我下一次編一個(gè)。
回復(fù)

使用道具 舉報(bào)

ID:96682 發(fā)表于 2016-6-10 00:58 | 顯示全部樓層
你的仿真圖只能使用采用的數(shù)碼管段碼。
回復(fù)

使用道具 舉報(bào)

ID:111634 發(fā)表于 2016-6-10 19:32 | 顯示全部樓層
yzwzfyz 發(fā)表于 2016-6-9 11:40
上圖的設(shè)計(jì)不是很好的:缺點(diǎn)如下:
1、用了6個(gè)(U2-U7),不經(jīng)濟(jì)。
改進(jìn),用一個(gè)晶體管陣列(一個(gè)IC里集 ...

請(qǐng)看一下我的回復(fù)。
回復(fù)

使用道具 舉報(bào)

ID:111634 發(fā)表于 2016-6-10 22:51 | 顯示全部樓層
wc86110 發(fā)表于 2016-6-10 00:58
你的仿真圖只能使用采用的數(shù)碼管段碼。

這個(gè)當(dāng)然!電路與程序是相配的,程序是根據(jù)電路和功能編寫的,任何案例都是如此。
回復(fù)

使用道具 舉報(bào)

ID:194701 發(fā)表于 2017-5-7 15:06 | 顯示全部樓層
讀懂了別人正確有效的電路和程序,才能找出自己電路和程序的錯(cuò)誤
回復(fù)

使用道具 舉報(bào)

本版積分規(guī)則

小黑屋|51黑電子論壇 |51黑電子論壇6群 QQ 管理員QQ:125739409;技術(shù)交流QQ群281945664

Powered by 單片機(jī)教程網(wǎng)

快速回復(fù) 返回頂部 返回列表