蓝桥杯单片机第九届省赛编程题(深夜学习——单片机)

news2024/11/26 13:32:41

一、根据硬件框图初始化好要使用的外设

  1. 推测出外设类型:

PCF8591、矩阵按键、AT24C02、LED、数码管(定时器)

  1. 创建工程模板:

(1)主函数:

#ifndef PBBLIC_H
#define PBBLIC_H

#include <STC15F2K60S2.H>

#define u8 unsigned char
#define u16 unsigned int
    
void Close_All();
    
#endif

(2)公共函数:

#ifndef PBBLIC_H
#define PBBLIC_H

#include <STC15F2K60S2.H>

#define u8 unsigned char
#define u16 unsigned int
    
void Close_All();
    
#endif
#include "Public.h"

/*
    向某个锁存器发送信息
*/
void Select(u8 cs,u8 s_data)
{
    P0 = s_data;
    P2 = P2 & 0x1f | (cs<<5);
    P2 &= 0x1f;
}

/*
    关闭无关设备
*/
void Close_All()
{
    //关闭蜂鸣器和继电器
    Select(5,0x00);
    //关闭LED
    Select(4,0xff);
    //清空数码管数据
    Select(7,0xff);
}
  1. LED灯:

(1)主函数:

#include "Public.h"
#include "Simple_Device.h"
void main()
{
    Close_All();
    LED_Show(0xff);
}

(2)LED函数:

#ifndef SIMPLE_DEVICE_H
#define SIMPLE_DEVICE_H

#include "Public.h"

void LED_Show(u8 l_data);
    
#endif
#include "Simple_Device.h"

/*
    根据输入的8位数显示LED,其中1为亮灯
*/
void LED_Show(u8 l_data)
{
    Select(4,~l_data);
}
  1. 数码管:

(1)主函数:

#include "Public.h"
#include "Simple_Device.h"
#include "timer.h"
#include "stdio.h"
#include "SEG.h"
u16 seg_delay;
//数码管
u8 COT[9],COD[8],PIS;
void Key_Proc();
void SEG_Proc();
void main()
{
    Close_All();
    Timer0_Init();
    while(1)
    {
        SEG_Proc();
    }
}

void SEG_Proc()
{
    if(seg_delay)return;
    seg_delay = 1;
    
    sprintf(COT,"%u%u",(u16)1234,(u16)5678);
    SEG_TSL(COT,COD);
}

void Timer0_Isr(void) interrupt 1
{
    if(++key_delay == 10)key_delay = 0;
    if(++seg_delay == 500)seg_delay = 0;
    
    SEG_Show(COD[PIS],PIS);
    if(++PIS == 8)PIS = 0;
}

(2)数码管函数:

#ifndef SEG_H
#define SEG_H

#include "Public.h"

void SEG_TSL(u8 *input,u8 *output);
void SEG_Show(u8 COD,u8 PIS);
#endif
#include "SEG.h"

code unsigned char Seg_Table[] = 
{
0xc0, //0
0xf9, //1
0xa4, //2
0xb0, //3
0x99, //4
0x92, //5
0x82, //6
0xf8, //7
0x80, //8
0x90, //9
0x88, //A
0x83, //b
0xc6, //C
0xa1, //d
0x86, //E
0x8e //F
};

/*
    输入字符串输出数码管代码
*/
void SEG_TSL(u8 *input,u8 *output)
{
    u8 i=0;
    for(i=0;i<8;i++)
    {
        switch(input[i])
        {
            case '0':output[i] = Seg_Table[0];break;
            case '1':output[i] = Seg_Table[1];break;
            case '2':output[i] = Seg_Table[2];break;
            case '3':output[i] = Seg_Table[3];break;
            case '4':output[i] = Seg_Table[4];break;
            case '5':output[i] = Seg_Table[5];break;
            case '6':output[i] = Seg_Table[6];break;
            case '7':output[i] = Seg_Table[7];break;
            case '8':output[i] = Seg_Table[8];break;
            case '9':output[i] = Seg_Table[9];break;
            default:output[i] = 0xff;
        }
    }
}

/*
    数码管显示函数
*/
void SEG_Show(u8 COD,u8 PIS)
{
    //消隐
    Select(7,0xff);
    //位选
    Select(6,0x01<<PIS);
    //段选
    Select(7,COD);
}
  1. 矩阵按键:

(1)主函数:

#include "Public.h"
#include "Simple_Device.h"
#include "timer.h"
#include "stdio.h"
#include "SEG.h"
u8 key_delay;
u16 seg_delay;
//数码管
u8 COT[9],COD[8],PIS;
void Key_Proc();
void SEG_Proc();
void main()
{
    Close_All();
    Timer0_Init();
    while(1)
    {
//        SEG_Proc();
        Key_Proc();
    }
}

void Key_Proc()
{
    u8 key_now,key_dwon;
    static u8 key_old;
    if(key_delay)return;
    key_delay = 1;
    
    key_now = M_key();
    key_dwon = key_now & (key_now ^ key_old);
    key_old = key_now;
    
    if(key_dwon)
    {
        sprintf(COT,"%u",(u16)key_dwon);
        SEG_TSL(COT,COD);
    }
}

void SEG_Proc()
{
    if(seg_delay)return;
    seg_delay = 1;
    
    sprintf(COT,"%u%u",(u16)1234,(u16)5678);
    SEG_TSL(COT,COD);
}

void Timer0_Isr(void) interrupt 1
{
    if(++key_delay == 10)key_delay = 0;
    if(++seg_delay == 500)seg_delay = 0;
    
    SEG_Show(COD[PIS],PIS);
    if(++PIS == 8)PIS = 0;
}

(2)按键检测函数:

#ifndef SIMPLE_DEVICE_H
#define SIMPLE_DEVICE_H

#include "Public.h"

void LED_Show(u8 l_data);
u8 M_key();    
#endif
#include "Simple_Device.h"

/*
    根据输入的8位数显示LED,其中1为亮灯
*/
void LED_Show(u8 l_data)
{
    Select(4,~l_data);
}

/*
    矩阵按键检测
*/
u8 M_key()
{
    u16 key_temp=0,i=0;
    //逐个置零,读取电平
    P44=0;P42=1;P35=1;P34=1;
    key_temp |= (P3&0x0f);
    P44=1;P42=0;P35=1;P34=1;
    key_temp = (key_temp<<4) | (P3&0x0f);
    P44=1;P42=1;P35=0;P34=1;
    key_temp = (key_temp<<4) | (P3&0x0f);
    P44=1;P42=1;P35=1;P34=0;
    key_temp = (key_temp<<4) | (P3&0x0f);
    
    //检测数据
    for(i=0;i<16;i++)
    {
        if((key_temp & (0x8000>>i)) == 0)
            return i+4;
    }
    return 0;
}
  1. PCF8591:

由于我常常会忘记设备地址、控制字节格式、应答信号,所以我常常会从从官方给的数据中的数据手册中获得信息:

目录:

地址:

命令字节:

应答信号:

数据与电压换算:

(1)主函数:

#include "Public.h"
#include "Simple_Device.h"
#include "timer.h"
#include "stdio.h"
#include "SEG.h"
#include "PCF8591.h"
u8 key_delay;
u16 seg_delay;
//数码管
u8 COT[9],COD[8],PIS;
void Key_Proc();
void SEG_Proc();
void main()
{
    Close_All();
    Timer0_Init();
    //确定输出为AIN3
    PCF8591_Write(0x03);
    while(1)
    {
        SEG_Proc();
//        Key_Proc();
    }
}

void Key_Proc()
{
    u8 key_now,key_dwon;
    static u8 key_old;
    if(key_delay)return;
    key_delay = 1;
    
    key_now = M_key();
    key_dwon = key_now & (key_now ^ key_old);
    key_old = key_now;
    
    if(key_dwon)
    {
        sprintf(COT,"%u",(u16)key_dwon);
        SEG_TSL(COT,COD);
    }
}

void SEG_Proc()
{
    u8 show_cot;
    if(seg_delay)return;
    seg_delay = 1;
    
    show_cot =     PCF8591_Read();
    sprintf(COT,"%u",(u16)show_cot);    
//    sprintf(COT,"%u%u",(u16)1234,(u16)5678);
    SEG_TSL(COT,COD);
}

void Timer0_Isr(void) interrupt 1
{
    if(++key_delay == 10)key_delay = 0;
    if(++seg_delay == 500)seg_delay = 0;
    
    SEG_Show(COD[PIS],PIS);
    if(++PIS == 8)PIS = 0;
}

(2)PCF8591函数

#ifndef PCF8591_H
#define PCF8591_H

#include "Public.h"
#include "iic.h"

void PCF8591_Write(u8 c_data);
u8 PCF8591_Read();
#endif
#include "PCF8591.h"

/*
    写入控制字节
*/
void PCF8591_Write(u8 c_data)
{
    IIC_Start();
    IIC_SendByte(0x90);
    IIC_WaitAck();
    IIC_SendByte(c_data);
    IIC_WaitAck();
    IIC_Stop();
}

/*
    读取数据字节
*/
u8 PCF8591_Read()
{
    u8 d_data;
    IIC_Start();
    IIC_SendByte(0x91);
    IIC_WaitAck();
    d_data = IIC_RecByte();
    IIC_SendAck(1);
    IIC_Stop();    
    return d_data;
}

(3)官方给的IIC驱动文件:

#ifndef _IIC_H
#define _IIC_H

#include "Public.h"
#include "intrins.h"

sbit SDA = P2^1;
sbit SCL = P2^0;

void IIC_Start(void); 
void IIC_Stop(void);  
bit IIC_WaitAck(void);  
void IIC_SendAck(bit ackbit); 
void IIC_SendByte(unsigned char byt); 
unsigned char IIC_RecByte(void); 

#endif
#include "iic.h"

#define DELAY_TIME 5

//
void IIC_Delay(unsigned char i)
{
    do{_nop_();}
    while(i--);        
}

//
void IIC_Start(void)
{
    SDA = 1;
    SCL = 1;
    IIC_Delay(DELAY_TIME);
    SDA = 0;
    IIC_Delay(DELAY_TIME);
    SCL = 0;    
}

//
void IIC_Stop(void)
{
    SDA = 0;
    SCL = 1;
    IIC_Delay(DELAY_TIME);
    SDA = 1;
    IIC_Delay(DELAY_TIME);
}

//
void IIC_SendAck(bit ackbit)
{
    SCL = 0;
    SDA = ackbit;                      
    IIC_Delay(DELAY_TIME);
    SCL = 1;
    IIC_Delay(DELAY_TIME);
    SCL = 0; 
    SDA = 1;
    IIC_Delay(DELAY_TIME);
}

//
bit IIC_WaitAck(void)
{
    bit ackbit;
    
    SCL  = 1;
    IIC_Delay(DELAY_TIME);
    ackbit = SDA;
    SCL = 0;
    IIC_Delay(DELAY_TIME);
    return ackbit;
}

//
void IIC_SendByte(unsigned char byt)
{
    unsigned char i;

    for(i=0; i<8; i++)
    {
        SCL  = 0;
        IIC_Delay(DELAY_TIME);
        if(byt & 0x80) SDA  = 1;
        else SDA  = 0;
        IIC_Delay(DELAY_TIME);
        SCL = 1;
        byt <<= 1;
        IIC_Delay(DELAY_TIME);
    }
    SCL  = 0;  
}

//
unsigned char IIC_RecByte(void)
{
    unsigned char i, da;
    for(i=0; i<8; i++)
    {   
        SCL = 1;
            IIC_Delay(DELAY_TIME);
            da <<= 1;
            if(SDA) da |= 1;
            SCL = 0;
            IIC_Delay(DELAY_TIME);
    }
    return da;    
}
  1. AT24C02:

设备地址:

写操作:

读操作:

(1)主函数:

#include "Public.h"
#include "Simple_Device.h"
#include "timer.h"
#include "stdio.h"
#include "SEG.h"
#include "PCF8591.h"
#include "AT24C02.h"
u8 key_delay;
u16 seg_delay;
//数码管
u8 COT[9],COD[8],PIS;
void Key_Proc();
void SEG_Proc();
void main()
{
    Close_All();
    Timer0_Init();
    while(1)
    {
        SEG_Proc();
//        Key_Proc();
    }
}

void Key_Proc()
{
    u8 key_now,key_dwon;
    static u8 key_old;
    if(key_delay)return;
    key_delay = 1;
    
    key_now = M_key();
    key_dwon = key_now & (key_now ^ key_old);
    key_old = key_now;
    
    if(key_dwon)
    {
        sprintf(COT,"%u",(u16)key_dwon);
        SEG_TSL(COT,COD);
    }
}
void Delay5ms()        //@12MHz
{
    unsigned char i, j;

    i = 59;
    j = 90;
    do
    {
        while (--j);
    } while (--i);
}


void SEG_Proc()
{
    static u8 num=0;
    u8 show_cot;
    if(seg_delay)return;
    seg_delay = 1;
    
    AT24C02_Write(0x01,num);
    Delay5ms();    
    show_cot = AT24C02_Read(0x01);
    sprintf(COT,"%u",(u16)show_cot);    
//    sprintf(COT,"%u%u",(u16)1234,(u16)5678);
    SEG_TSL(COT,COD);
    num++;
}

void Timer0_Isr(void) interrupt 1
{
    if(++key_delay == 10)key_delay = 0;
    if(++seg_delay == 500)seg_delay = 0;
    
    SEG_Show(COD[PIS],PIS);
    if(++PIS == 8)PIS = 0;
}

(2)AT24C02函数:

#ifndef AT24C02_H
#define AT24C02_H

#include "Public.h"
#include "iic.h"

void AT24C02_Write(u8 w_addr,u8 w_data);
u8 AT24C02_Read(u8 r_addr);

#endif
#include "AT24C02.h"

void AT24C02_Write(u8 w_addr,u8 w_data)
{
    IIC_Start();
    IIC_SendByte(0xa0);
    IIC_WaitAck();
    IIC_SendByte(w_addr);
    IIC_WaitAck();
    IIC_SendByte(w_data);
    IIC_WaitAck();    
    IIC_Stop();
}

u8 AT24C02_Read(u8 r_addr)
{
    u8 r_data;
    IIC_Start();
    IIC_SendByte(0xa0);
    IIC_WaitAck();
    IIC_SendByte(r_addr);
    IIC_WaitAck();
    IIC_Start();
    IIC_SendByte(0xa1);
    IIC_WaitAck();
    r_data = IIC_RecByte();
    IIC_SendAck(1);    
    IIC_Stop();
    return r_data;
}

二、实现功能:

由于我们是靠按键改变模式的,所以我们可以从按键函数出发,补充各种功能。

  1. 基本功能框架:

按键可以分为两种:功能按键和切换按键,搭建框架则要抓住切换按键。

由上面两图我们可以知道,显示模式分为非显示模式、设置模式和亮度显示模式,其中设置模式又分为三种状态。

(1)部分主函数:

void main()
{
    Close_All();
    Timer0_Init();
    
    while(1)
    {
//        SEG_Proc();
        Key_Proc();
        LED_Show(0x01<<(set_mode+5));
    }
}

void Key_Proc()
{
    u8 key_now,key_dwon,key_up;
    static u8 key_old;
    if(key_delay)return;
    key_delay = 1;
    
    key_now = M_key();
    key_dwon = key_now & (key_now ^ key_old);
    key_up = ~key_now & (key_now ^ key_old);
    key_old = key_now;
    
    if(key_dwon == 7)
    {
        
    }
    
    else if(key_dwon == 6)
    {
        if(++set_mode == 3)set_mode = 0;
        LED_Show(0x01<<(set_mode+5));
        
    }
    
    else if(key_dwon == 5)
    {
        
    }    

    else if(key_dwon == 4)
    {
        if(set_mode == 0)
        {
            seg_mode = 1;
            LED_Show(seg_mode);
        }
    }
    else if(key_up == 4)    
    {
        if(set_mode == 0)
        {
            seg_mode = 0;
            LED_Show(seg_mode);
        }
    }
}
  1. 非设置模式:

(1)部分主函数:

#include "Public.h"
#include "Simple_Device.h"
#include "timer.h"
#include "stdio.h"
#include "SEG.h"
#include "PCF8591.h"
#include "AT24C02.h"
u8 key_delay;
u16 seg_delay;
//数码管
u8 COT[9],COD[8],PIS;
//模式
u8 seg_mode,set_mode;
//非设置模式
u16 led_time=400,l_count_ms,p_count_ms;
u8 l_data,l_power=1,led_mode,turn_sign=1;

void Key_Proc()
{
    u8 key_now,key_dwon,key_up;
    static u8 key_old;
    if(key_delay)return;
    key_delay = 1;
    
    key_now = M_key();
    key_dwon = key_now & (key_now ^ key_old);
    key_up = ~key_now & (key_now ^ key_old);
    key_old = key_now;
    
    if(key_dwon == 7)
    {
        turn_sign ^= 1;
    }
    
    else if(key_dwon == 6)
    {
        if(++set_mode == 3)
        {
            set_mode = 0;
            seg_mode = 0;
        }
        else
            seg_mode = 1;
        
    }
    
    else if(key_dwon == 5)
    {
        
    }    

    else if(key_dwon == 4)
    {
        if(set_mode == 0)
        {
            seg_mode = 2;
        }
    }
    else if(key_up == 4)    
    {
        if(set_mode == 0)
        {
            seg_mode = 0;
        }
    }
  
}


void SEG_Proc()
{
    u8 show_cot;
    if(seg_delay)return;
    seg_delay = 1;
    
    //非设置模式,数码管不显示任何东西
    if(seg_mode == 0)
    {
        sprintf(COT,"");    
        PCF8591_Proc();
    }
    
//    sprintf(COT,"%u   %u",(u16)l_power,(u16)l_temp);
    SEG_TSL(COT,COD);

}

void Timer0_Isr(void) interrupt 1
{
    l_count_ms++;
    p_count_ms++;
    if(++key_delay == 10)key_delay = 0;
    if(++seg_delay == 500)seg_delay = 0;
    
    SEG_Show(COD[PIS],PIS);
    if(++PIS == 8)PIS = 0;
    
    if(set_mode == 0)
    {
        if(p_count_ms < 10*0.25*l_power)
            LED_Show(l_data);    
        else
            LED_Show(0x00);
         if(p_count_ms == 10)
            p_count_ms = 0;
    }
    else
        LED_Show(0x00);
}

void LED_Proc()
{
    static u8 led_temp;
    if(l_count_ms < led_time || !turn_sign )return;
    l_count_ms = 0;
    
    if(led_mode == 0)
    {
        l_data = 0x01<<led_temp;
        led_temp++;
        if(led_temp == 8)
        {
            led_temp = 0;
            led_mode = 1;
        }
    }
    else if(led_mode == 1)
    {
        l_data = 0x80>>led_temp; 
        led_temp++;
        if(led_temp == 8)
        {
            led_temp = 0;
            led_mode = 2;
        }
    }
    else if(led_mode == 2)
    {
        l_data = (0x80>>led_temp) | (0x01<<led_temp); 
        led_temp++;
        if(led_temp == 4)
        {
            led_temp = 0;
            led_mode = 3;
        }
    }
    else if(led_mode == 3)
    {
        l_data = (0x08>>led_temp) | (0x10<<led_temp); 
        led_temp++;
        if(led_temp == 4)
        {
            led_temp = 0;
            led_mode = 0;
        }
    }    
}
  1. 亮度显示模式:

(1)部分主函数:

#include "Public.h"
#include "Simple_Device.h"
#include "timer.h"
#include "stdio.h"
#include "SEG.h"
#include "PCF8591.h"
#include "AT24C02.h"
u8 key_delay;
u16 seg_delay;
//数码管
u8 COT[9],COD[8],PIS;
//模式
u8 seg_mode,set_mode;
//非设置模式
u16 led_time=400,l_count_ms,p_count_ms;
u8 l_data,l_power=1,led_mode,turn_sign=1;

void Key_Proc()
{
    u8 key_now,key_dwon,key_up;
    static u8 key_old;
    if(key_delay)return;
    key_delay = 1;
    
    key_now = M_key();
    key_dwon = key_now & (key_now ^ key_old);
    key_up = (~key_now) & (key_now ^ key_old);
    key_old = key_now;
    
    if(key_dwon == 7)
    {
        turn_sign ^= 1;
    }
    
    else if(key_dwon == 6)
    {
        if(++set_mode == 3)
        {
            set_mode = 0;
            seg_mode = 0;
        }
        else
            seg_mode = 1;
        
    }
    
    else if(key_dwon == 5)
    {
        
    }    

    else if(key_dwon == 4)
    {
        if(seg_mode == 0)
        {
            seg_mode = 2;
        }
        
    }
    else if(key_up == 4)    
    {
        if(seg_mode == 2)
        {
            seg_mode = 0;
        }

    }
    
}


void SEG_Proc()
{
    u8 show_cot;
    if(seg_delay)return;
    seg_delay = 1;
    
    //非设置模式,数码管不显示任何东西
    if(seg_mode == 0)
    {
        sprintf(COT,"        ");    
    }
    if(seg_mode == 2)
    {
        sprintf(COT,"      %02u",(u16)l_power);
    }
//    sprintf(COT,"%u   %u",(u16)l_power,(u16)l_temp);
    SEG_TSL(COT,COD);

}

void Timer0_Isr(void) interrupt 1
{
    l_count_ms++;
    p_count_ms++;
    if(++key_delay == 10)key_delay = 0;
    if(++seg_delay == 500)seg_delay = 0;
    
    SEG_Show(COD[PIS],PIS);
    if(++PIS == 8)PIS = 0;
    
    if(set_mode == 0)
    {
        PCF8591_Proc();
        if(p_count_ms < 10*0.25*l_power)
            LED_Show(l_data);    
        else
            LED_Show(0x00);
         if(p_count_ms == 10)
            p_count_ms = 0;
    }
    else
        LED_Show(0x00);
}

void LED_Proc()
{
    static u8 led_temp;
    if(l_count_ms < led_time || !turn_sign )return;
    l_count_ms = 0;
    

    if(led_mode == 0)
    {
        l_data = 0x01<<led_temp;
        led_temp++;
        if(led_temp == 8)
        {
            led_temp = 0;
            led_mode = 1;
        }
    }
    else if(led_mode == 1)
    {
        l_data = 0x80>>led_temp; 
        led_temp++;
        if(led_temp == 8)
        {
            led_temp = 0;
            led_mode = 2;
        }
    }
    else if(led_mode == 2)
    {
        l_data = (0x80>>led_temp) | (0x01<<led_temp); 
        led_temp++;
        if(led_temp == 4)
        {
            led_temp = 0;
            led_mode = 3;
        }
    }
    else if(led_mode == 3)
    {
        l_data = (0x08>>led_temp) | (0x10<<led_temp); 
        led_temp++;
        if(led_temp == 4)
        {
            led_temp = 0;
            led_mode = 0;
        }
    }    
}


  1. 设置模式:

(1)部分主函数:

#include "Public.h"
#include "Simple_Device.h"
#include "timer.h"
#include "stdio.h"
#include "SEG.h"
#include "PCF8591.h"
#include "AT24C02.h"
u8 key_delay;
u16 seg_delay;
//数码管
u8 COT[9],COD[8],PIS;
//模式
u8 seg_mode,set_mode;
//非设置模式
u16 led_time=400,l_count_ms,p_count_ms;
u8 l_data,l_power=1,led_mode=1,turn_sign=1;
u8 flash_sign , led_temp;

void Key_Proc()
{
    u8 key_now,key_dwon,key_up;
    static u8 key_old;
    if(key_delay)return;
    key_delay = 1;
    
    key_now = M_key();
    key_dwon = key_now & (key_now ^ key_old);
    key_up = (~key_now) & (key_now ^ key_old);
    key_old = key_now;
    
    if(key_dwon == 7)
    {
        turn_sign ^= 1;
    }
    
    else if(key_dwon == 6)
    {
        if(++set_mode == 3)
        {
            set_mode = 0;
            seg_mode = 0;
            //重新计数
            l_count_ms = 0;
            p_count_ms = 0;
            //闪烁标志更新
            flash_sign = 0;
            l_data = 0;
            led_temp = 0;
        }
        else
            seg_mode = 1;
    }
    
    else if(key_dwon == 5)
    {
        switch(set_mode)
        {
            case 1:led_mode++;
                break;
            case 2:led_time+=100;
                break;            
        }
        //上边界属性
        if(led_mode == 5)led_mode = 1;
        if(led_time == 1300)led_time = 400;
    }    

    else if(key_dwon == 4)
    {
        if(seg_mode == 0)
        {
            seg_mode = 2;
        }
        switch(set_mode)
        {
            case 1:led_mode--;
                break;
            case 2:led_time-=100;
                break;            
        }
        //下边界属性
        if(led_mode == 0)led_mode = 4;
        if(led_time == 300)led_time = 1200;
    }
    else if(key_up == 4)    
    {
        if(seg_mode == 2)
        {
            seg_mode = 0;
        }
    }
    
}


void SEG_Proc()
{
    if(seg_delay)return;
    seg_delay = 1;
    
    //非设置模式,数码管不显示任何东西
    if(seg_mode == 0)
    {
        sprintf(COT,"        ");    
    }
    if(seg_mode == 1)
    {
        
        if(set_mode == 1 && flash_sign == 1)
        {
            sprintf(COT,"    %4u",(u16)led_time);
            flash_sign = 0;
        }
        else if(set_mode == 2 && flash_sign == 1)
        {
            sprintf(COT,"0%1u0     ",(u16)led_mode);
            flash_sign = 0;
        }
        else
        {
            sprintf(COT,"0%1u0 %4u",(u16)led_mode,(u16)led_time);
            flash_sign = 1; 
        }
    }
    if(seg_mode == 2)
    {
        sprintf(COT,"      %02u",(u16)l_power);
    }
    SEG_TSL(COT,COD);

}

补充:(忘记实现AT24C02功能)

void main()
{
    Close_All();
    Timer0_Init();
    //选择AIN3输出
    PCF8591_Write(0x03);
    AT24C02_Proc();
    while(1)
    {
        SEG_Proc();
        Key_Proc();
        LED_Proc();
    }
}

void Key_Proc()
{
    u8 key_now,key_dwon,key_up;
    static u8 key_old;
    if(key_delay)return;
    key_delay = 1;
    
    key_now = M_key();
    key_dwon = key_now & (key_now ^ key_old);
    key_up = (~key_now) & (key_now ^ key_old);
    key_old = key_now;
    
    if(key_dwon == 7)
    {
        turn_sign ^= 1;
    }
    
    else if(key_dwon == 6)
    {
        if(++set_mode == 3)
        {
            set_mode = 0;
            seg_mode = 0;
            //重新计数
            l_count_ms = 0;
            p_count_ms = 0;
            //闪烁标志更新
            flash_sign = 0;
            l_data = 0;
            led_temp = 0;
            //保存信息到EEPROM
            at24_data[0] = led_mode;
            at24_data[1] = led_time>>8;//高八位
            at24_data[2] = led_time&0x00ff;//低八位
            AT24C02_Write(0x01,at24_data,3);
        }
        else
            seg_mode = 1;
    }
    
    else if(key_dwon == 5)
    {
        switch(set_mode)
        {
            case 1:led_mode++;
                break;
            case 2:led_time+=100;
                break;            
        }
        //上边界属性
        if(led_mode >= 5)led_mode = 1;
        if(led_time >= 1300)led_time = 400;
    }    

    else if(key_dwon == 4)
    {
        if(seg_mode == 0)
        {
            seg_mode = 2;
        }
        switch(set_mode)
        {
            case 1:led_mode--;
                break;
            case 2:led_time-=100;
                break;            
        }
        //下边界属性
        if(led_mode <= 0)led_mode = 4;
        if(led_time <= 300)led_time = 1200;
    }
    else if(key_up == 4)    
    {
        if(seg_mode == 2)
        {
            seg_mode = 0;
        }
    }
    
}
void AT24C02_Proc()
{
    AT24C02_Read(0x01,at24_data,3);
    led_mode = at24_data[0];
    led_time = ((at24_data[1]<<8) | at24_data[2]);
}

三、参考代码:

  1. 主函数:

#include "Public.h"
#include "Simple_Device.h"
#include "timer.h"
#include "stdio.h"
#include "SEG.h"
#include "PCF8591.h"
#include "AT24C02.h"
u8 key_delay;
u16 seg_delay;
//数码管
u8 COT[9],COD[8],PIS;
//模式
u8 seg_mode,set_mode;
//非设置模式
u16 led_time=400,l_count_ms,p_count_ms;
u8 l_data,l_power=1,led_mode=1,turn_sign=1;
u8 flash_sign    , led_temp;
//EEPROM
u8 at24_data[3];
void Key_Proc();
void SEG_Proc();
void LED_Proc();
void PCF8591_Proc();
void AT24C02_Proc();
void main()
{
    Close_All();
    Timer0_Init();
    //选择AIN3输出
    PCF8591_Write(0x03);
    AT24C02_Proc();
    while(1)
    {
        SEG_Proc();
        Key_Proc();
        LED_Proc();
    }
}

void Key_Proc()
{
    u8 key_now,key_dwon,key_up;
    static u8 key_old;
    if(key_delay)return;
    key_delay = 1;
    
    key_now = M_key();
    key_dwon = key_now & (key_now ^ key_old);
    key_up = (~key_now) & (key_now ^ key_old);
    key_old = key_now;
    
    if(key_dwon == 7)
    {
        turn_sign ^= 1;
    }
    
    else if(key_dwon == 6)
    {
        if(++set_mode == 3)
        {
            set_mode = 0;
            seg_mode = 0;
            //重新计数
            l_count_ms = 0;
            p_count_ms = 0;
            //闪烁标志更新
            flash_sign = 0;
            l_data = 0;
            led_temp = 0;
            //保存信息到EEPROM
            at24_data[0] = led_mode;
            at24_data[1] = led_time>>8;//高八位
            at24_data[2] = led_time&0x00ff;//低八位
            AT24C02_Write(0x01,at24_data,3);
        }
        else
            seg_mode = 1;
    }
    
    else if(key_dwon == 5)
    {
        switch(set_mode)
        {
            case 1:led_mode++;
                break;
            case 2:led_time+=100;
                break;            
        }
        //上边界属性
        if(led_mode >= 5)led_mode = 1;
        if(led_time >= 1300)led_time = 400;
    }    

    else if(key_dwon == 4)
    {
        if(seg_mode == 0)
        {
            seg_mode = 2;
        }
        switch(set_mode)
        {
            case 1:led_mode--;
                break;
            case 2:led_time-=100;
                break;            
        }
        //下边界属性
        if(led_mode <= 0)led_mode = 4;
        if(led_time <= 300)led_time = 1200;
    }
    else if(key_up == 4)    
    {
        if(seg_mode == 2)
        {
            seg_mode = 0;
        }
    }
    
}


void SEG_Proc()
{
    if(seg_delay)return;
    seg_delay = 1;
    
    //非设置模式,数码管不显示任何东西
    if(seg_mode == 0)
    {
        sprintf(COT,"        ");    
    }
    if(seg_mode == 1)
    {
        
        if(set_mode == 1 && flash_sign == 1)
        {
            sprintf(COT,"    %4u",(u16)led_time);
            flash_sign = 0;
        }
        else if(set_mode == 2 && flash_sign == 1)
        {
            sprintf(COT,"0%1u0     ",(u16)led_mode);
            flash_sign = 0;
        }
        else
        {
            sprintf(COT,"0%1u0 %4u",(u16)led_mode,(u16)led_time);
            flash_sign = 1; 
        }
    }
    if(seg_mode == 2)
    {
        sprintf(COT,"      %02u",(u16)l_power);
    }
    SEG_TSL(COT,COD);

}

void Timer0_Isr(void) interrupt 1
{
    l_count_ms++;
    p_count_ms++;
    if(++key_delay == 10)key_delay = 0;
    if(++seg_delay == 800)seg_delay = 0;
    
    SEG_Show(COD[PIS],PIS);
    if(++PIS == 8)PIS = 0;
    
    if(set_mode == 0)
    {
        if(p_count_ms < 10*0.25*l_power)
            LED_Show(l_data);    
        else
            LED_Show(0x00);
         if(p_count_ms == 10)
            p_count_ms = 0;
    }
    else
        LED_Show(0x00);
}

void LED_Proc()
{
    if(l_count_ms < led_time || !turn_sign )return;
    l_count_ms = 0;
    
    PCF8591_Proc();
    if(led_mode == 1)
    {
        l_data = 0x01<<led_temp;
        led_temp++;
        if(led_temp == 8)
        {
            led_temp = 0;
        }
    }
    else if(led_mode == 2)
    {
        l_data = 0x80>>led_temp; 
        led_temp++;
        if(led_temp == 8)
        {
            led_temp = 0;
        }
    }
    else if(led_mode == 3)
    {
        l_data = (0x80>>led_temp) | (0x01<<led_temp); 
        led_temp++;
        if(led_temp == 4)
        {
            led_temp = 0;
        }
    }
    else if(led_mode == 4)
    {
        l_data = (0x08>>led_temp) | (0x10<<led_temp); 
        led_temp++;
        if(led_temp == 4)
        {
            led_temp = 0;
        }
    }    
}

void PCF8591_Proc()
{
    float pcf_data=0,i=0;    
    pcf_data = PCF8591_Read()/256.0*5;
    for(i=0;i<4;i++)
        if(pcf_data<=1.6*i)
        {
            l_power = i+1;
            return;
        }
}

void AT24C02_Proc()
{
    AT24C02_Read(0x01,at24_data,3);
    led_mode = at24_data[0];
    led_time = ((at24_data[1]<<8) | at24_data[2]);
}
  1. 公共函数:

#ifndef PBBLIC_H
#define PBBLIC_H

#include <STC15F2K60S2.H>

#define u8 unsigned char
#define u16 unsigned int
    
void Close_All();
void Select(u8 cs,u8 s_data);    
#endif
#include "Public.h"

/*
    向某个锁存器发送信息
*/
void Select(u8 cs,u8 s_data)
{
    P0 = s_data;
    P2 = P2 & 0x1f | (cs<<5);
    P2 &= 0x1f;
}

/*
    关闭无关设备
*/
void Close_All()
{
    //关闭蜂鸣器和继电器
    Select(5,0x00);
    //关闭LED
    Select(4,0xff);
    //清空数码管数据
    Select(7,0xff);
}
  1. 简单外设:

#ifndef SIMPLE_DEVICE_H
#define SIMPLE_DEVICE_H

#include "Public.h"

void LED_Show(u8 l_data);
u8 M_key();    
#endif
#include "Simple_Device.h"

/*
    根据输入的8位数显示LED,其中1为亮灯
*/
void LED_Show(u8 l_data)
{
    Select(4,~l_data);
}

/*
    矩阵按键检测
*/
u8 M_key()
{
    u16 key_temp=0,i=0;
    //逐个置零,读取电平
    P44=0;P42=1;P35=1;P34=1;
    key_temp |= (P3&0x0f);
    P44=1;P42=0;P35=1;P34=1;
    key_temp = (key_temp<<4) | (P3&0x0f);
    P44=1;P42=1;P35=0;P34=1;
    key_temp = (key_temp<<4) | (P3&0x0f);
    P44=1;P42=1;P35=1;P34=0;
    key_temp = (key_temp<<4) | (P3&0x0f);
    
    //检测数据
    for(i=0;i<16;i++)
    {
        if((key_temp & (0x8000>>i)) == 0)
            return i+4;
    }
    return 0;
}
  1. 定时器

#ifndef TIME_H
#define TIME_H

#include "Public.h"

void Timer0_Init(void);    
#endif
#include "timer.h"



void Timer0_Init(void)        //1毫秒@12.000MHz
{
    AUXR |= 0x80;            //定时器时钟1T模式
    TMOD &= 0xF0;            //设置定时器模式
    TL0 = 0x20;                //设置定时初始值
    TH0 = 0xD1;                //设置定时初始值
    TF0 = 0;                //清除TF0标志
    TR0 = 1;                //定时器0开始计时
    ET0 = 1;                //使能定时器0中断
    EA = 1;
}

  1. 数码管:

#ifndef SEG_H
#define SEG_H

#include "Public.h"

void SEG_TSL(u8 *input,u8 *output);
void SEG_Show(u8 COD,u8 PIS);
#endif
#include "SEG.h"

code unsigned char Seg_Table[] = 
{
0xc0, //0
0xf9, //1
0xa4, //2
0xb0, //3
0x99, //4
0x92, //5
0x82, //6
0xf8, //7
0x80, //8
0x90, //9
0x88, //A
0x83, //b
0xc6, //C
0xa1, //d
0x86, //E
0x8e //F
};

/*
    输入字符串输出数码管代码
*/
void SEG_TSL(u8 *input,u8 *output)
{
    u8 i=0;
    for(i=0;i<8;i++)
    {
        switch(input[i])
        {
            case '0':output[i] = Seg_Table[0];break;
            case '1':output[i] = Seg_Table[1];break;
            case '2':output[i] = Seg_Table[2];break;
            case '3':output[i] = Seg_Table[3];break;
            case '4':output[i] = Seg_Table[4];break;
            case '5':output[i] = Seg_Table[5];break;
            case '6':output[i] = Seg_Table[6];break;
            case '7':output[i] = Seg_Table[7];break;
            case '8':output[i] = Seg_Table[8];break;
            case '9':output[i] = Seg_Table[9];break;
            default:output[i] = 0xff;
        }
    }
}

/*
    数码管显示函数
*/
void SEG_Show(u8 COD,u8 PIS)
{
    //消隐
    Select(7,0xff);
    //位选
    Select(6,0x01<<PIS);
    //段选
    Select(7,COD);
}
  1. PCF8591:

#ifndef PCF8591_H
#define PCF8591_H

#include "Public.h"
#include "iic.h"

void PCF8591_Write(u8 c_data);
u8 PCF8591_Read();
#endif
#include "PCF8591.h"

/*
    写入控制字节
*/
void PCF8591_Write(u8 c_data)
{
    IIC_Start();
    IIC_SendByte(0x90);
    IIC_WaitAck();
    IIC_SendByte(c_data);
    IIC_WaitAck();
    IIC_Stop();
}

/*
    读取数据字节
*/
u8 PCF8591_Read()
{
    u8 d_data;
    IIC_Start();
    IIC_SendByte(0x91);
    IIC_WaitAck();
    d_data = IIC_RecByte();
    IIC_SendAck(1);
    IIC_Stop();    
    return d_data;
}
  1. AT24C02:

#ifndef AT24C02_H
#define AT24C02_H

#include "Public.h"
#include "iic.h"

void AT24C02_Write(u8 w_addr,u8 *w_data,u8 num);
void AT24C02_Read(u8 r_addr,u8 *r_data,u8 num);
void AT24C02_Write1(u8 w_addr,u8 w_data);
u8 AT24C02_Read1(u8 r_addr);
void Delay5ms() ;
#endif
#include "AT24C02.h"

void Delay5ms()        //@12MHz
{
    unsigned char i, j;

    i = 59;
    j = 90;
    do
    {
        while (--j);
    } while (--i);
}


void AT24C02_Write(u8 w_addr,u8 *w_data,u8 num)
{
    IIC_Start();
    IIC_SendByte(0xa0);
    IIC_WaitAck();
    IIC_SendByte(w_addr);
    IIC_WaitAck();
    while(num--)
    {
        IIC_SendByte(*w_data);
        w_data++;
        IIC_WaitAck();    
        Delay5ms();
    }
    IIC_Stop();
}

void AT24C02_Read(u8 r_addr,u8 *r_data,u8 num)
{
    IIC_Start();
    IIC_SendByte(0xa0);
    IIC_WaitAck();
    IIC_SendByte(r_addr);
    IIC_WaitAck();
    IIC_Start();
    IIC_SendByte(0xa1);
    IIC_WaitAck();
    while(num--)
    {
        *r_data = IIC_RecByte();
        r_data++;
        if(num == 0)
            IIC_SendAck(1);
        else
            IIC_SendAck(0);    
    }
    IIC_Stop();
}
  1. IIC

#ifndef _IIC_H
#define _IIC_H

#include "Public.h"
#include "intrins.h"

sbit SDA = P2^1;
sbit SCL = P2^0;

void IIC_Start(void); 
void IIC_Stop(void);  
bit IIC_WaitAck(void);  
void IIC_SendAck(bit ackbit); 
void IIC_SendByte(unsigned char byt); 
unsigned char IIC_RecByte(void); 
void IIC_Delay(unsigned char i);
#endif
#include "iic.h"

#define DELAY_TIME 5

//
void IIC_Delay(unsigned char i)
{
    do{_nop_();}
    while(i--);        
}

//
void IIC_Start(void)
{
    SDA = 1;
    SCL = 1;
    IIC_Delay(DELAY_TIME);
    SDA = 0;
    IIC_Delay(DELAY_TIME);
    SCL = 0;    
}

//
void IIC_Stop(void)
{
    SDA = 0;
    SCL = 1;
    IIC_Delay(DELAY_TIME);
    SDA = 1;
    IIC_Delay(DELAY_TIME);
}

//
void IIC_SendAck(bit ackbit)
{
    SCL = 0;
    SDA = ackbit;                      
    IIC_Delay(DELAY_TIME);
    SCL = 1;
    IIC_Delay(DELAY_TIME);
    SCL = 0; 
    SDA = 1;
    IIC_Delay(DELAY_TIME);
}

//
bit IIC_WaitAck(void)
{
    bit ackbit;
    
    SCL  = 1;
    IIC_Delay(DELAY_TIME);
    ackbit = SDA;
    SCL = 0;
    IIC_Delay(DELAY_TIME);
    return ackbit;
}

//
void IIC_SendByte(unsigned char byt)
{
    unsigned char i;

    for(i=0; i<8; i++)
    {
        SCL  = 0;
        IIC_Delay(DELAY_TIME);
        if(byt & 0x80) SDA  = 1;
        else SDA  = 0;
        IIC_Delay(DELAY_TIME);
        SCL = 1;
        byt <<= 1;
        IIC_Delay(DELAY_TIME);
    }
    SCL  = 0;  
}

//
unsigned char IIC_RecByte(void)
{
    unsigned char i, da;
    for(i=0; i<8; i++)
    {   
        SCL = 1;
            IIC_Delay(DELAY_TIME);
            da <<= 1;
            if(SDA) da |= 1;
            SCL = 0;
            IIC_Delay(DELAY_TIME);
    }
    return da;    
}

四、收获:

  1. 利用STC-ISP初始化定时器时要注意开中断

  1. 初始化模块的时候最好先初始化数码管

  1. IIC写一次时间大概要5ms,不能刚进行写操作后就进行读操作,在测试模块时要着重注意

  1. 重新设置模式时记得重新计数

5、做完后记得检查有没有模块没用,有没有功能没实现

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/401026.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

SpaceNet 建筑物检测

SpaceNet 建筑物检测 该存储库提供了一些 python 脚本和 jupyter 笔记本来训练和评估从SpaceNet卫星图像中提取建筑物的卷积神经网络。 用法

直播回顾 | 聚焦科技自立自强,Bonree ONE 助力国产办公自动化平稳替代

3月5日&#xff0c;两会发布《政府工作报告》&#xff0c;强调科技政策要聚焦自立自强。 统计显示&#xff0c;2022年金融信创项目数同比增长300%&#xff0c;金融领域信创建设当前已进入发展爆发期&#xff0c;由国有大型银行逐渐向中小型银行、非银金融机构不断扩展。信创云…

全生命周期的云原生安全框架

本博客地址&#xff1a;https://security.blog.csdn.net/article/details/129423036 一、全生命周期的云原生安全框架 如图所示&#xff1a; 二、框架说明 在上图中&#xff0c;我们从两个维度描述各个安全机制&#xff0c;横轴是开发和运营阶段&#xff0c;细分为编码、测试…

Grial UI Kit updated Crack

Grial UI Kit updated Crack 增加了“电影”流&#xff0c;该流由3个屏幕组成&#xff0c;呈现平滑过渡和动画的电影目录。 添加了新的栅格导航栏控件&#xff0c;允许您使任何页面导航栏透明&#xff0c;也可以从带有实心导航栏的页面导航到带有透明导航栏的网页&#xff0c;反…

指针数组 数组指针 常量指针 指针常量 函数指针 指针函数

一、指针常量与常量指针 1、指针常量 本质上是一个常量&#xff0c;常量的类型是指针&#xff0c;表示该常量是一个指针类型的常量。在指针常量中&#xff0c;指针本身的值是一个常量&#xff0c;不可以改变&#xff0c;始终指向同一个地址。在定义的时候&#xff0c;必须要初…

npm安装依赖和package.json版本不一致解决

npm或者cnpm 安装依赖&#xff0c;不会完全按照package.json中的版本号来&#xff0c;会有稍微的差异&#xff0c;这样的差异可能导致项目起不来&#xff0c;或者报错&#xff0c; 因为某些包只有特定的版本才能正常运行。 解决方案 npm提供了shrinkwrap命令来解决这个问题。 …

opencv-图像几何处理

缩放 缩放只是调整图像的大小。为此&#xff0c;opencv提供了一个cv2.resize()函数&#xff0c;可以手动指定图像大小&#xff0c;也可以指定缩放因子。你可以使用任意一种方法调整图像的大小&#xff1a; import cv2 from matplotlib import pyplot as pltlogo cv2.imread(…

害我走了8年弯路,接口测试和性能测试的区别原来是这几点,终于点通了......

目录&#xff1a;导读前言一、Python编程入门到精通二、接口自动化项目实战三、Web自动化项目实战四、App自动化项目实战五、一线大厂简历六、测试开发DevOps体系七、常用自动化测试工具八、JMeter性能测试九、总结&#xff08;尾部小惊喜&#xff09;前言 性能测试和接口测试…

Allegro如何知道组合操作命令的拼写

Allegro如何知道组合操作命令的拼写 前面介绍了如何知道单个操作命令的拼写,但如果是复合命令,就无法直观的通过命令来了解,如下图 Snap Pick to -Segment这个命令拼写是什么 如何知道,具体操作如下 点击File点击Script 出现Scripting窗口

itextpdf生成报文总结

1.使用itextpdfgradle引入依赖compile ("com.itextpdf:itextpdf:5.5.13") compile ("com.itextpdf:itext-asian:5.2.0") compile ("com.itextpdf.tool:xmlworker:5.5.13")参考&#xff1a;https://www.cnblogs.com/ssslinppp/p/4976922.htmlhttp…

Linux性能补丁升级,避免不必要的跨核Wake-Up

导读一个由英特尔发起的、旨在改进Linux内核公平调度程序代码的补丁系列&#xff0c;也看到了来自AMD工程师和其他利益相关者的测试/反馈&#xff0c;并继续进行改进。这个补丁系列的重点是避免在不必要的情况下发生过多的跨核唤醒(Cross-CPU Wake-up)。这样一来&#xff0c;这…

Unity合批处理

一.静态合批标记为Batching Static的物体&#xff08;标记后物体运行不能移动、旋转、缩放&#xff09;在使用相同材质球的条件下在项目打包的时候unity会自动将这些物体合并到一个大Mesh*缺点打包后体积增大运行时内存占用增大二.动态批处理不超过300个顶点不超过900个属性不包…

手机通讯录--课后程序(Python程序开发案例教程-黑马程序员编著-第5章-课后作业)

实例2&#xff1a;手机通讯录 通讯录是记录了联系人姓名和联系方式的名录&#xff0c;手机通讯录是最常见的通讯录之一&#xff0c;人们可以在通讯录中通过姓名查看相关联系人的联系方式、邮箱、地址等信息&#xff0c;也可以在其中新增联系人&#xff0c;或修改、删除联系人信…

MySQL高级—约束与关系

&#x1f34e;道阻且长&#xff0c;行则将至。&#x1f353; 目录 一、约束 1.约束的基本概念 2.分类 二、关系 1.一对多 2.多对多 3.一对一 三、多表查询 1.多查 2.连接查询 3.子查询 一、约束 1.约束的基本概念 数据库的表示用来存储数据的&#xff0c;为了保证…

PID控制算法详解

1. 前言 PID 即 Proportional&#xff08;比例&#xff09;&#xff0c;Integral&#xff08;积分&#xff09;&#xff0c;Differential&#xff08;微分&#xff09;的英文缩写。顾名思义&#xff0c;PID 控制算法是结合比例&#xff0c;积分和微分三种环节于一体的自动控制…

cs231n计算机视觉课程-(数据驱动方法)

姿态、环境、遮挡这些问题算法都因该是robust 课程中提到具体写一个识别猫咪的算法是不稳定的&#xff0c;容易出错的。 所以提出了Data-Driven Approach的方法 一个是训练函数&#xff0c; 这函数接受图片和标签&#xff0c;然后输出标签 另一个则是预测函数&#xff0c;输…

团队管理的七个要点

要掌握团队管理的要点和做好团队管理工作&#xff0c;不是一件容易的事&#xff0c;但也远非想象中那么难。首先&#xff0c;我个人比较推荐所有团队管理者都能阅读下《经理人参阅&#xff1a;团队管理》&#xff08;注意该书仅可其官网获得&#xff09;这本佳作。相信会为你带…

vue ssr的hydration问题

我的网站百家饭OpenAPI平台是vuepress写的&#xff0c;前段时间我还写了个专栏讲了vuepress2.0教学。 最开始我们的网站是类似公司网站的情况&#xff0c;以介绍为主&#xff0c;后来又加了一个openapi编辑器&#xff0c;编辑器主要在一个页面里面&#xff0c;vuepress还勉强可…

【Springboot系列】Springboot接管所有Controller,magic-api源码阅读

系列文章地址&#xff1a;Spring Boot学习大纲&#xff0c;可以留言自己想了解的技术点 最近在项目中使用了一个第三方的包 magic-api&#xff0c;节省了很多的时间&#xff0c;整体来说就是只用写sql就好了&#xff0c;不用写service&#xff0c;controller那些&#xff0c;全…

Flink从入门到精通系列(二)

3、Flink 部署 Flink 是一个非常灵活的处理框架&#xff0c;它支持多种不同的部署场景&#xff0c;还可以和不同的资源管 理平台方便地集成。 3.1、快速启动一个 Flink 集群 3.1.1、环境配置 Flink 是一个分布式的流处理框架&#xff0c;所以实际应用一般都需要搭建集群环境…