【蓝桥杯—单片机学习笔记(十)】定时器实现秒表功能

本文是蓝桥杯单片机学习笔记的一部分,主要介绍了如何在CT107D训练平台上使用定时器T0来设计一个带有分-秒-毫秒显示的秒表。秒表具备清零、暂停和启动功能,通过S4和S5两个独立按键进行控制,其中S4用于暂停和启动,S5用于清零。程序实现中涉及到了单片机的定时器配置和按键处理逻辑。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

一、要求

在CT107D单片机综合训练平台上,利用定时器T0、数码管模块和2个独立按键(J5的2、3短接),设计一个秒表,具有清零、暂停、启动功能。

1. 显示格式为:分-秒-毫秒(50ms)。

2. 独立按键S4为:暂停或启动;独立按键S5为:清零。按键均为按下有效。

二、程序

#include <reg52.h>
#include <intrins.h>

#define uchar unsigned char
    
sbit s5 = P3^2;
sbit s4 = P3^3;
    
uchar code table[] = {0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,
                       0x80,0x90,0x88,0x80,0xc6,0xc0,0x86,0x8e,
                       0xbf,0xff};//共阳段码表
uchar ms = 0;   //定义毫秒
uchar s = 0;    //定义秒
uchar fen = 0;    //定义分
                       
void delay_ms(uchar xms)		//@11.0592MHz
{
	uchar i,j;
    while(xms)
    {    
        _nop_();
        _nop_();
        _nop_();
        i = 11;
        j = 190;
        do
        {
            while (--j);
        } while (--i);
        xms--;
    }
}

void channel_select(uchar n)    //通道选择
{
    switch(n)
    {
        case 4 : 
            P2 = (P2 & 0x1f) | 0x80;
        break;
        case 5 : 
            P2 = (P2 & 0x1f) | 0xa0;
        break;
        case 6: 
            P2 = (P2 & 0x1f) | 0xc0;
        break;
        case 7 : 
            P2 = (P2 & 0x1f) | 0xe0;
        break;
    }
}



void SMG_display_bit(uchar channel,uchar num)   //选择第几个数码管显示什么数字
{
    channel_select(6);
    P0 = 0x01 << channel;
    channel_select(7);
    P0 = num;
}

void SMG_display()  //数码管秒表显示
{
    
    //-----------显示ms---------------
    SMG_display_bit(6,table[ms/10]);
    delay_ms(2);
    SMG_display_bit(7,table[ms%10]);
    delay_ms(2);
    SMG_display_bit(5,table[16]);
    delay_ms(2);
    
    //-----------显示s---------------
    SMG_display_bit(3,table[s/10]);
    delay_ms(2);
    SMG_display_bit(4,table[s%10]);
    delay_ms(2);
    SMG_display_bit(2,table[16]);
    delay_ms(2);
    
    //-----------显示fen---------------
    SMG_display_bit(0,table[fen/10]);
    delay_ms(2);
    SMG_display_bit(1,table[fen%10]);
    delay_ms(2);
}

void key_scanf()    //按键扫描
{
    if(s4 == 0)
    {
        delay_ms(50);
        {
            if(s4 == 0)
               TR0 = ~TR0; 
        }
        while(s4 == 0)
            SMG_display();
    }
    
    if(s5 == 0)
    {
        delay_ms(50);
        {
            if(s5 == 0)
            {
                ms = 0;
                s = 0;
                fen = 0;
            } 
        }
        while(s5 == 0)
            SMG_display();
    }
}

void system_init()  //系统初始化
{
    channel_select(4);  //关闭LED
    P0 = 0xff;
    channel_select(5);  //关闭蜂鸣器和继电器
    P0 = 0x00;
}

void timer0_init()  //定时器0初始化
{
    TMOD = 0x01;    //设置定时器0工作方式为方式0
    EA = 1; //开总中断
    TH0 = (65536 - 50000)/256;  //预置初值
    TL0 = (65536 * 50000)%256;
    ET0 = 1;    //允许定时器0中断
    TR0 = 1;    //开定时器0      
}

void main()
{
    system_init();
    timer0_init();
    while(1)
    {
        key_scanf();
        SMG_display();
    }
}


void service_timer0() interrupt 1   //中断服务函数
{
    TH0 = (65536 - 50000)/256;  //重装初值
    TL0 = (65536 * 50000)%256;
    ms++;
    if(ms == 20)    //50ms*20 = 1000ms
    {
        ms = 0;
        s++;
        if(s == 60)
        {
            s = 0;
            fen++;
            if(fen == 99)
                fen = 0;
        }
    }
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

单片机学习之路

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值