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

QQ登錄

只需一步,快速開(kāi)始

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

單片機(jī)簡(jiǎn)易密碼鎖判斷程序一直錯(cuò)誤,無(wú)法判斷按下的三個(gè)按鍵是否正確,怎么回事?

[復(fù)制鏈接]
ID:626711 發(fā)表于 2019-10-19 19:11 | 顯示全部樓層 |閱讀模式
簡(jiǎn)易的單片機(jī)密碼鎖用不了,使用的是靜態(tài)數(shù)碼管+矩陣按鍵+蜂鳴器+繼電器
自己寫(xiě)的程序,下載到單片機(jī)后按鍵可以使用,按下一個(gè)按鍵,數(shù)碼管會(huì)正常顯示按鍵按下對(duì)應(yīng)的字符,但按了123后蜂鳴器和繼電器沒(méi)有反應(yīng),下面是我寫(xiě)的單片機(jī)程序(附件有單片機(jī)原理圖和實(shí)物圖)


#include "reg52.h"

#define jian_pan P1
#define shumaguan P0

sbit buzzer=P2^3;   //蜂鳴器
sbit relay=P2^2;     //繼電器

int data password[4];
unsigned char cunfang;  //存放矩陣鍵盤(pán)按下的位置對(duì)應(yīng)的0~f字符
unsigned char code number[17]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,
                                        0x7f,0x6f,0x77,0x7c,0x39,0x5e,0x79,0x71};//顯示0~F的值  共陰

void delay(unsigned long int i)             //延時(shí)函數(shù)
{
  while(i--);
}

void keydown()          //檢測(cè)哪個(gè)按鍵按下
{
        int a=0;
        jian_pan=0x0f;
        if(jian_pan!=0x0f)
        {
          delay(100);//延時(shí)10ms
          if(jian_pan!=0x0f)
          {
                    //測(cè)試列
                 jian_pan=0x0f;
                 switch(jian_pan)
                  {
                   case(0x07) : cunfang=0;break;
                   case(0x0b) : cunfang=4;break;
                   case(0x0d) : cunfang=8;break;
                   case(0x0e) : cunfang=12;break;
                  }
                  //測(cè)試行
                  jian_pan=0xf0;
                  switch(jian_pan)
                   {
                   case(0x70) : cunfang=cunfang;break;
                   case(0xb0) : cunfang=cunfang+1;break;
                   case(0xd0) : cunfang=cunfang+2;break;
                   case(0xe0) : cunfang=cunfang+3;break;
                   }
                  while((a<50)&&(jian_pan!=0xf0))
                  {
                          delay(1000); //延時(shí)100ms
                        a++;
                  }
             }
        }
}

void judge_number()    //檢測(cè)按下的三次是否依次為123
{
   int mi_ma=0,n;
   if(cunfang!=0)       //判斷存放按鍵的數(shù)值是否為零,當(dāng)不為零的話相當(dāng)于輸入了一位密碼
   {
     mi_ma=mi_ma+1;                //記錄按下的次數(shù)
          password[mi_ma]=cunfang;   //把按下的密碼存放到數(shù)組中
  if(mi_ma==3)                      //判斷是否按下了三次
   {
    password[0]=password[1]*100+password[2]*10+password[3];   把前三次輸入的數(shù)字合并
    if(password[0]==123)   //設(shè)置正確密碼是123 并判斷用戶輸入的密碼是否為123       】
        {                                                                                                                  |
         buzzer=0;                                                                                                    |
         for(n=0;n<1000;n++)                                                                                   |    當(dāng)密碼輸入正確繼電器打開(kāi),蜂鳴器響
          {                                                                                                                |
                  relay=~relay;                                                                                        |
                delay(10);                                                                                             |
          }                                                                                                                】
          delay(6553400);                                       //延時(shí)約1分鐘相當(dāng)于開(kāi)鎖一分鐘
         }
    }
   }
}

void main()
{
  while(1)
  {
   keydown(); //判斷鍵入的字符
   shumaguan=~number[cunfang];//數(shù)碼管顯示按下的字符
   judge_number();  //檢測(cè)按下的三次是否依次為123
  }
}




開(kāi)發(fā)板

開(kāi)發(fā)板

EM3_V3.0原理圖.pdf

316.22 KB, 下載次數(shù): 7

原理圖

回復(fù)

使用道具 舉報(bào)

ID:491577 發(fā)表于 2019-10-20 10:18 | 顯示全部樓層
你的程序是按下1按鍵后一直輸出1直到松開(kāi)按鍵為止,void judge_number()  這個(gè)函數(shù)是只要有按鍵按下就一直累加,按1就是1一直累加,累加3次之后得到3個(gè)1,如果你把密碼改成111,就可以打開(kāi)繼電器了。修改的方法:void judge_number() 中加入判斷保證每按下一個(gè)按鍵只累加一次,才可以得到你想要的結(jié)果。
回復(fù)

使用道具 舉報(bào)

ID:626711 發(fā)表于 2019-10-20 18:32 | 顯示全部樓層
hhh402 發(fā)表于 2019-10-20 10:18
你的程序是按下1按鍵后一直輸出1直到松開(kāi)按鍵為止,void judge_number()  這個(gè)函數(shù)是只要有按鍵按下就一直 ...

還是不行,把密碼改成111,不管是長(zhǎng)按111還是短按111繼電器都不會(huì)打開(kāi)
我的keydown();函數(shù)按下一次應(yīng)該是只能返回一個(gè)數(shù)字
回復(fù)

使用道具 舉報(bào)

ID:626711 發(fā)表于 2019-10-20 19:05 | 顯示全部樓層
hhh402 發(fā)表于 2019-10-20 10:18
你的程序是按下1按鍵后一直輸出1直到松開(kāi)按鍵為止,void judge_number()  這個(gè)函數(shù)是只要有按鍵按下就一直 ...

還是不行,我把密碼改成111,無(wú)論是長(zhǎng)按111還是短按111,繼電器都不會(huì)打開(kāi)
keydown()函數(shù)應(yīng)該一次只能得到一個(gè)數(shù)值
回復(fù)

使用道具 舉報(bào)

ID:491577 發(fā)表于 2019-10-21 11:48 | 顯示全部樓層
void judge_number()函數(shù)中的變量 int mi_ma=0;是局部變量,每運(yùn)行一次都會(huì)重新初始化為0,mi_ma永遠(yuǎn)為零,要改成:   
void judge_number()    //檢測(cè)按下的三次是否依次為123
{
   static int mi_ma=0,a1=0;    int n;
   if(cunfang!=0)       //判斷存放按鍵的數(shù)值是否為零,當(dāng)不為零的話相當(dāng)于輸入了一位密碼
   {  if(a1==0)   //這個(gè)與else a1=1;配合保證每次按鍵只計(jì)算一次。a1必須是靜態(tài)變量或全局變量。
       {
           a1=1;
          mi_ma=mi_ma+1;                //記錄按下的次數(shù)
          password[mi_ma]=cunfang;   //把按下的密碼存放到數(shù)組中
       }
     else a1=0;
/*上面這7行(if    else語(yǔ)句)是保證每次按鍵只計(jì)算一次,原理:原來(lái)a1=0,第一次按鍵時(shí)if語(yǔ)句運(yùn)行一次后a1=1,以后就不會(huì)再運(yùn)行if里面的語(yǔ)句     了,直到按鍵釋放后a1才會(huì)等于0,如此循環(huán)。這個(gè)語(yǔ)句要牢記,處理按鍵時(shí)都會(huì)用到。注意:這個(gè)語(yǔ)句里面的變量必須是靜態(tài)變量或全局變量。
*/
   }
if(mi_ma==3)                      //判斷是否按下了三次
   {
    mi_ma=0; //復(fù)位
    password[0]=password[1]*100+password[2]*10+password[3];   把前三次輸入的數(shù)字合并
    if(password[0]==123)   //設(shè)置正確密碼是123 并判斷用戶輸入的密碼是否為123       】
        {                                                                                                                  |
         buzzer=0;                                                                                                    |
         for(n=0;n<1000;n++)                                                                                   |    當(dāng)密碼輸入正確繼電器打開(kāi),蜂鳴器響
          {                                                                                                                |
                  relay=~relay;                                                                                        |
                delay(10);                                                                                             |
          }                                                                                                                】
          delay(6553400);                                       //延時(shí)約1分鐘相當(dāng)于開(kāi)鎖一分鐘
         }
   }
}
回復(fù)

使用道具 舉報(bào)

ID:626711 發(fā)表于 2019-10-22 13:25 | 顯示全部樓層
hhh402 發(fā)表于 2019-10-21 11:48
void judge_number()函數(shù)中的變量 int mi_ma=0;是局部變量,每運(yùn)行一次都會(huì)重新初始化為0,mi_ma永遠(yuǎn)為零, ...

還是不行,不過(guò)把密碼改成111可以工作
回復(fù)

使用道具 舉報(bào)

ID:626711 發(fā)表于 2019-10-22 13:43 | 顯示全部樓層
hhh402 發(fā)表于 2019-10-21 11:48
void judge_number()函數(shù)中的變量 int mi_ma=0;是局部變量,每運(yùn)行一次都會(huì)重新初始化為0,mi_ma永遠(yuǎn)為零, ...

我知道這次的問(wèn)題出在哪兒了,當(dāng)我按下1的時(shí)候
if(cunfang!=0)       //判斷存放按鍵的數(shù)值是否為零,當(dāng)不為零的話相當(dāng)于輸入了一位密碼
   {  if(a1==0)   //這個(gè)與else a1=1;配合保證每次按鍵只計(jì)算一次。a1必須是靜態(tài)變量或全局變量。
       {
           a1=1;
          mi_ma=mi_ma+1;                //記錄按下的次數(shù)
          password[mi_ma]=cunfang;   //把按下的密碼存放到數(shù)組中
       }
     else a1=0;
第一次循環(huán)的時(shí)候記錄下我的密碼1,然后我還沒(méi)松開(kāi)的時(shí)候他第二次循環(huán)就來(lái)了這次把a(bǔ)1變成零,然后緊接著第三次循環(huán)記錄下第二位密碼還是1,我按下1的那一會(huì)兒它會(huì)循環(huán)很多次,然后都相當(dāng)于密碼是111
給這個(gè)     else a1=0;
改成再加一個(gè)判斷語(yǔ)句,把矩陣鍵盤(pán)的數(shù)據(jù)傳送進(jìn)來(lái),判斷矩陣鍵盤(pán)是否松開(kāi)松開(kāi)的話a1=0
回復(fù)

使用道具 舉報(bào)

本版積分規(guī)則

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

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

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