蓝桥杯C51(试题内容学习)

news2024/10/5 14:21:07

因为C51只有一组数码管,但是我们需要显示的东西有很多,所以通过按键切换是我们必须要知道的

按键之间有嵌套,切换,计数,对于按键的使用我们是必须知道的

1. HC573锁存器的选择

我们在之前的基础上对其进行了优化,这样就不会出现冲突的问题

因为在使用前,我们直接把所有的给关闭了,当使用的时候先把P0给起来,在引到每个锁存器

/************锁存器选择******************
功能:打通功能需要的锁存器
参数:channel(选择锁存器) dat(一般为oxff 打开通道,但是我们可以去掉这个参数)
***************************************/
void SelectHC573(unsigned channel,unsigned char dat)
{
    P0 = dat;  //带设置参数数据
	switch(channel)
	{
		case 4:
			P2 = (P2 & 0x1f) | 0x80;		//Y4,选择LED控制
		break;
		case 5:
			P2 = (P2 & 0x1f) | 0xa0;		//Y5,选择蜂鸣器和继电器控制
		break;
		case 6:
			P2 = (P2 & 0x1f) | 0xc0;		//Y6,选择数码管位置
		break;
		case 7:
			P2 = (P2 & 0x1f) | 0xe0;		//Y7,选择数码管段码
		break;
		case 0:
			P2 = (P2 & 0x1f) | 0x00;		//在完成后关闭所有锁存器
		break;
	}
     P2 = (P2 & 0x1f) | 0x00;              // 修改完成,关闭全部锁存器    
}

2. 数码管位置选择与数码管显示

<1> 数码管选择是需要延时函数的。我们是利用余辉效果来进行显示的,所以在数码管显示之后我们需要进行延时,所以我们直接把延时函数放到单个数码管显示之后,这样子显示就变得简单了

<2>延时延时可以选择 char / int 两种类型,但是需要注意时间,如果时间太长会导致抖动,如果时间过短又会导致数码管变暗。

/****************数码管延时函数**************
功能:对数码管进行延时
参数:t--
*******************************************/

void DelaySMG(unsigned int t)
{
   while(t--);
}

/*************数码管显示函数***************
功能: 控制每个数码管的亮暗,在之前的基础上我们使用了延时函数,这样在主体显示就不用添加延时函数了
参数: value (内容) pos(位置)
****************************************/
void DisplaySMG_Bit(unsigned char value, unsigned char pos)
{
     SelectHC573(6,0x01<<pos);  //数码管段位
//P0 = 0X01 << pos
     SelectHC573(7,value);      //数码管内容
//P0 = value
     DelaySMG(500);             //延时
     SelectHC573(6,0x01<<pos);  //数码管段位
     SelectHC573(7,0xff);      //数码管消隐
}


//如果前面的锁存器没有设置P0的参数,则可以使用下面的老办法
void DisplaySMG_Bit(unsigned char value, unsigned char pos)
{
	P0 = 0xff;						//消隐
	SelectHC573(6);
	P0 = 0x01 << pos;			    //位置	
	SelectHC573(7);
	P0 = value;						//内容
}

/************控制全数码管*************
功能:在显示前后进行使用,进行数码管的初始化
参数 value(一般为0xff)
************************************/
void DisPlaySMG_All(unsigned char value)
{
  SelectHC573(6, 0xff);  //数码管段位
  SelectHC573(7,value);  //数码管内容   
}

既然需要控制数码管,我们就需要不同的标志位来进行记录

/***********数码管显示内容选择***********
功能:通过改变flag的参数来选择不同的锁存器
参数:无
***************************************/
void DisplaySMG_Select()
{
   switch(SMG_flag)
   {
		 case 1:
		 (显示时间的函数 DisplayTime);
         break;
		 
		 case 2:
	     (显示温度的函数 DisplayTemp);
		 break;
....

   }
}

3. 独立按键进行切换

只进行切换当前模式,不能改变当前的状态,所以我们需要在更换模式时,仍然保持数码管的显示,而进行标志位值的改变,当模式多时,我们就需要使用矩阵按键(参考上一篇文章的扫描)

/*****************按键切换**********
功能:通过按键切换模式,也就是我们之前写过的
参数:无
**********************************/
void Key_Scan()
{
	if(S4 == 0)
		{
			Delay(200);                //消抖
			if(S4 == 0)
			{
				if(stat_flag == 1)     //初始默认的标志位为1——系统时间记录
				{
					stat_flag =2;      //转换模式类型
				}
				while(S4 == 0)
				{
					Display_SMGselect(); //按键按下后仍然能显示当前的数码管,这步是需要的
					Delay(500);
				}
			}
		}
 //模仿上面的操作,进行数码管的操作
   else if(S5 == 0)
		{
			Delay(200);
			if(S5 == 0)
			{
				if(stat_flag == 2)
				{
					stat_flag =1;
				}
				while(S5 == 0)
				{
				  Display_SMGselect();
					Delay(500);
				}
			}
		}
}

而进行切换的过程中,我们当前状态需要一直进行的,我们就在while循环中执行

4. 系统初始化函数

/*==================系统初始化函数======================
功能:关闭没用的器件,打开需要使用的。进行锁存器的选择
参数:无
=======================================================*/
void InitSystem()
{
	SelectHC573(5);   //关闭蜂鸣器,继电器
	P0 = 0x00;
	SelectHC573(4);   //打开灯光
	P0 = 0xff;
	SelectHC573(0);   //完成后关闭
}

5. 系统时间函数

我们通过定时器来进行时间计数,通过测试,按键切换不会改变系统运行时间的值,我们不需要记载,他会一直记录着

/*================定时器初始化函数====================
功能: 初始化定时器
参数: 无
=======================================================*/
void InitTimer0()
{
	TMOD = 0x21;			       // 定时器1/2一起赋值
	TH0 = (65535 - 50000) / 256;   // 0,05s
	TL0 = (65535 - 50000) % 256;

	ET0 = 1;					//使能定时器T0
	EA = 1;						//使能总中断
	TR0 = 1;					//启动定时器T0
}


/*===============定时器服务函数===================
功能:利用定时器进行计数
参数:无
=======================================================*/
void ServiceTimer0() interrupt 1
{
	TH0 = (65535 - 50000) / 256; //0.05s
	TL0 = (65535 - 50000) % 256;
	
	count++;
	if(count == 20)
	{
		count = 0;
		t_s++;
	}
	if(t_s == 60)
	{
		t_s = 0;
		t_m++;
		if(t_m == 60)
		{
			t_m = 0;
			t_h++;
		}
	}
}

6.系统时间函数显示

中断初始化的配置:

 <1> 配置工作模式,即对TMOD寄存器编程。
 <2> 计算技术初值,即对THx和TLx寄存器进行赋值。
 <3> 使能定时/计数器中断,即ET0或ET1置1。
 <4> 打开总中断,即EA =1。
 <5> 启动定时器,即TR0或TR1置1。

中断服务函数:

<1> 如果不是自动重装模式,需要对THx和TLx重新赋值。
<2> 进行间隔定时到达的逻辑处理(越少越好)
 

void DisplayTime()
{    
//注意的是,如果使用新版的数码管显示函数,就不再需要再延时了
    DisPlay_All(0xff);      //消隐
	DisplaySMG_Bit(SMG_NoDot[t_s%10],7);		
	DelaySMG(500);
	DisplaySMG_Bit(SMG_NoDot[t_s/10],6);	
	DelaySMG(500);
	DisplaySMG_Bit(SMG_NoDot[16],5);				
	DelaySMG(500);
	
	DisplaySMG_Bit(SMG_NoDot[t_m%10],4);		
	DelaySMG(500);
	DisplaySMG_Bit(SMG_NoDot[t_m/10],3);		
	DelaySMG(500);
	DisplaySMG_Bit(SMG_NoDot[16],2);				
	DelaySMG(500);
	
	DisplaySMG_Bit(SMG_NoDot[t_h%10],1);		
	DelaySMG(500);
	DisplaySMG_Bit(SMG_NoDot[t_h/10],0);		
	DelaySMG(500);
	DisPlay_All(0xff);     //结尾再来一次
}

同时,在老师的视频内容中有说到,在延时的时候需要继续显示一下数码管的内容

void DisplayTmp(unsigned int t)
{
    while(t--)
   {
     DisplayTemp();
    }
]

实际测试之后,我们没有在温度显示函数里面再进行延时,也是可以正常显示的

7- 温度读取函数

/*********温度读取函数************
功能:进行温度读取(具体在上一篇文章讲过,之后会把内容移动过来)
参数:无
******************************/
void Read_DS18B20_temp()
{
	unsigned char LSB,MSB;
	
	init_ds18b20();
	Write_DS18B20(0XCC);
	Write_DS18B20(0X44);
	
	//Delay_temp(1000);
	
	init_ds18b20();
	Write_DS18B20(0XCC);
	Write_DS18B20(0Xbe);
	
	LSB = Read_DS18B20();
	MSB = Read_DS18B20();
	
	temp = 0x000;
	temp = MSB;
	temp <<= 8;
	temp = temp | LSB;
	
	if((temp & 0xf800) == 0x0000)
	{
		temp>>=4;
		
		temp = temp *10;
		temp = temp +(LSB&0x0f)*0.625;
	}
	
}

需要注意的是,在数码管显示温度之前,我们都要在显示函数前进行温度的读取,也就是把它写在 DisplayTemp 前面

温度显示函数

void DisplayTemp()
{
    Read_DS18B20_temp();    
    DisPlay_All(0xff);    
	ShowSMG_bit(7,SMGnodot_CA[temp%10]);
	DelaySMG(400);
	ShowSMG_bit(6,SMGdot_CA[(temp%100)/10]);
	DelaySMG(400);
	ShowSMG_bit(5,SMGnodot_CA[temp/100]);
	DelaySMG(400);
	
	ShowSMG_bit(4,0XFF);
	DelaySMG(400);
	ShowSMG_bit(3,0XFF);
	DelaySMG(400);
	ShowSMG_bit(2,0XFF);
	DelaySMG(400);
	ShowSMG_bit(1,0XFF);
	DelaySMG(400);
	ShowSMG_bit(0,0XFF);
	DelaySMG(400);
    DisPlay_All(0xff);   
}  

DS18B20 温度的底层代码

onewire.c文件

#include "onewire.h"
#include "reg52.h"

sbit DQ = P1^4;  


void Delay_OneWire(unsigned int t)  
{
	while(t--);
}


void Write_DS18B20(unsigned char dat)
{
	char i;
	for(i=0;i<8;i++)
	{
		DQ = 0;
		DQ = dat&0x01;
		Delay_OneWire(50);
		DQ = 1;
		dat >>= 1;
	}
	Delay_OneWire(50
	);
}


unsigned char Read_DS18B20(void)
{
	unsigned char i;
	unsigned char dat;
  
	for(i=0;i<8;i++)
	{
		DQ = 0;
		dat >>= 1;
		DQ = 1;
		if(DQ)
		{
			dat |= 0x80;
		}	    
		Delay_OneWire(50);
	}
	return dat;
}


bit init_ds18b20(void)
{
  	bit initflag = 0;
  	
  	DQ = 1;
  	Delay_OneWire(120);
  	DQ = 0;
  	Delay_OneWire(800);
  	DQ = 1;
  	Delay_OneWire(100); 
    initflag = DQ;     
  	Delay_OneWire(50);
  
  	return initflag;
}

onewire.h文件

我们之后也可以把前面写的函数给封装到文件里

#ifndef __ONEWIRE_H
#define __ONEWIRE_H


unsigned char rd_temperature(void);  
bit init_ds18b20(void); 
void Write_DS18B20(unsigned char dat);
unsigned char Read_DS18B20(void);
	
#endif

8-实时时钟DS1302

DS1302有关日历和时钟的寄存器有12个,我们最常用的有7个。

 

 什么是BCD码?
   就是用十六进制来表示十进制。什么意思?怎么理解?
   例如,十六进制数0x13的值为整数19,但BCD码表示的是整数13

 DS1302将地址和读写控制放到一个字节里面,形成一个控制字,格式如下:

我们往DS1304里面写入一个8为的数据(指令),把它分为上面8个

 通过上面的控制字格式,大家就可以明白为什么DS1302读寄存器和写寄存器的地址是不一样的了,因为这个地址包含了读写控制位。为了方便程序设计,我们把

读寄存器地址写寄存器地址日历时钟寄存器方面用三个数组定义。

BCD码,用16进制来表示10进制  

0x30(秒) 0x50(50分) 如上图所示,依次类推

底层驱动代码实现可参考如下:

DS1302.c

unsigned char DS1302_ReadByte(unsigned char addr)
{
        unsigned char n,dat,tmp;
        RST = 0;
        _nop_();
        SCLK = 0;
        _nop_();
        RST = 1;
        _nop_();

        for(n=0; n<8; n++)         //发送要读出数据的内存地址
        {
                DSIO = addr & 0x01;
                addr >>= 1;
                SCLK = 1;
                _nop_();
                SCLK = 0;
                _nop_();
        }
        
        for(n=0; n<8; n++)         //读出该地址内存的数据
        {
                tmp = DSIO;
                dat = (dat>>1) | (tmp<<7);
                SCLK = 1;
                _nop_();
                SCLK = 0;
                _nop_();
        }

        RST = 0;
        _nop_();
        SCLK = 1;
        _nop_();
        DSIO = 0;
        _nop_();
        DSIO = 1;
        _nop_();
        return dat;        
}

void DS1302_WriteByte(unsigned char addr, unsigned char dat)
{
        unsigned char n;
        RST = 0;
        _nop_();
        SCLK = 0;
        _nop_();
        RST = 1;
        _nop_();        

        for (n=0; n<8; n++)         //发送要写入数据的内存地址
        {
                DSIO = addr & 0x01;
                addr >>= 1;
                SCLK = 1;
                _nop_();
                SCLK = 0;
                _nop_();
        }
        for (n=0; n<8; n++)         //将指定内容写入该地址的内存
        {
                DSIO = dat & 0x01;
                dat >>= 1;
                SCLK = 1;
                _nop_();
                SCLK = 0;
                _nop_();
        }                 
        RST = 0;
        _nop_();
}

有了上面两个SPI底层代码,我们读出DS1302的数据就变得非常简单了

我们可以参考下面的源码:

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

sbit HC138_A = P2^5;        
sbit HC138_B = P2^6;        
sbit HC138_C = P2^7;        

sbit SCLK = P1^7; 
sbit RST =  P1^3; 
sbit DSIO = P2^3;
unsigned char code READ_RTC_ADDR[7] = {0x81, 0x83, 0x85, 0x87, 0x89, 0x8b, 0x8d};
unsigned char code WRITE_RTC_ADDR[7] = {0x80, 0x82, 0x84, 0x86, 0x88, 0x8a, 0x8c};
unsigned char TIME[7] = {0x30, 0x50, 0x23, 0x17, 0x02, 0x06, 0x18};

unsigned char code SMG_NoDot[18] = 
    {0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,
     0x80,0x90,0x88,0x80,0xc6,0xc0,0x86,0x8e,
     0xbf,0x7f};

void DelaySMG(unsigned int time)
{
        while(time--);
}

void Init74HC138(unsigned char n)
{
        switch(n)
        {
                case 4:
                        HC138_A = 0;
                        HC138_B = 0;
                        HC138_C = 1;
                        break;
                case 5:
                        HC138_A = 1;
                        HC138_B = 0;
                        HC138_C = 1;
                        break;
                case 6:
                        HC138_A = 0;
                        HC138_B = 1;
                        HC138_C = 1;
                        break;
                case 7:
                        HC138_A = 1;
                        HC138_B = 1;
                        HC138_C = 1;
                        break;
                case 8:
                        HC138_A = 0;
                        HC138_B = 0;
                        HC138_C = 0;
                        break;
        }
}

void DispaySMG_Bit(unsigned char value, unsigned char pos)
{
        Init74HC138(6);
        P0 = (0x01 << pos);
        Init74HC138(7);
        P0 = value;
}

void DS1302_WriteByte(unsigned char addr, unsigned char dat)
{
        unsigned char n;
        RST = 0;
        _nop_();
        SCLK = 0;
        _nop_();
        RST = 1;
        _nop_();        

        for (n=0; n<8; n++)
        {
                DSIO = addr & 0x01;
                addr >>= 1;
                SCLK = 1;
                _nop_();
                SCLK = 0;
                _nop_();
        }
        for (n=0; n<8; n++)
        {
                DSIO = dat & 0x01;
                dat >>= 1;
                SCLK = 1;
                _nop_();
                SCLK = 0;
                _nop_();
        }                 
        RST = 0;
        _nop_();
}

unsigned char DS1302_ReadByte(unsigned char addr)
{
        unsigned char n,dat,tmp;
        RST = 0;
        _nop_();
        SCLK = 0;
        _nop_();
        RST = 1;
        _nop_();

        for(n=0; n<8; n++)
        {
                DSIO = addr & 0x01;
                addr >>= 1;
                SCLK = 1;
                _nop_();
                SCLK = 0;
                _nop_();
        }
        
        for(n=0; n<8; n++)
        {
                tmp = DSIO;
                dat = (dat>>1) | (tmp<<7);
                SCLK = 1;
                _nop_();
                SCLK = 0;
                _nop_();
        }

        RST = 0;
        _nop_();
        SCLK = 1;
        _nop_();
        DSIO = 0;
        _nop_();
        DSIO = 1;
        _nop_();
        return dat;        
}


//DS1302的初始化
void DS1302_Config()
{
        unsigned char n;
        DS1302_WriteByte(0x8E,0x00); //写入保护
        for (n=0; n<7; n++) 
        {
               //写入时分秒年月日
                DS1302_WriteByte(WRITE_RTC_ADDR[n],TIME[n]);        
        }
        DS1302_WriteByte(0x8E,0x80); 
}

//DS1302读取当前时间
void DS1302_ReadTime()
{
        unsigned char n;
        for (n=0; n<7; n++) 
        {     
               //读取的内存地址,读7个时分秒年月日
                TIME[n] = DS1302_ReadByte(READ_RTC_ADDR[n]);
        }                
}

//数码管显示年月日
void XMF_ShowRealTime()
{
 //小时
        DispaySMG_Bit(SMG_NoDot[TIME[2]/16],0);        
        DelaySMG(500);
        DispaySMG_Bit(0xff,0);                        
        DispaySMG_Bit(SMG_NoDot[TIME[2]&0x0f],1);
        DelaySMG(500);
        DispaySMG_Bit(0xff,1);
        DispaySMG_Bit(SMG_NoDot[16],2);
        DelaySMG(500);
        DispaySMG_Bit(0xff,2);

//分钟
        DispaySMG_Bit(SMG_NoDot[TIME[1]/16],3);
        DelaySMG(500);
        DispaySMG_Bit(0xff,3);
        DispaySMG_Bit(SMG_NoDot[TIME[1]&0x0f],4);
        DelaySMG(500);
        DispaySMG_Bit(0xff,4);
        DispaySMG_Bit(SMG_NoDot[16],5);
        DelaySMG(500);
        DispaySMG_Bit(0xff,5);

//秒
        DispaySMG_Bit(SMG_NoDot[TIME[0]/16],6);
        DelaySMG(500);

        DispaySMG_Bit(0xff,6); //消隐
        DispaySMG_Bit(SMG_NoDot[TIME[0]&0x0f],7); //&0x0f可以改为 %16
        DelaySMG(500);
//关闭全部数码管,不关闭会导致亮度可能不同
        DispaySMG_Bit(0xff,7);
}


void main()
{
        DS1302_Config(); //DS1302初始化
        while(1)
        { 
          // 显示前需要先读取1302的数据
                DS1302_ReadTime();
                XMF_ShowRealTime();
        }
}

9- 串口中断

TH1TL1:设置波特率参数。
TMOD:设置定时器1的工作模式。
SBUF:串行通信数据的发送和接收缓冲器。
SCON:串行接口控制寄存器。

TR1: 定时器

ES: 串口中断

EA: 总中断

/*=================串口初始化函数========================
功能:将串口设置为模式1,波特率9600,允许接收
参数
=======================================================*/
void InitUart()
{
	TMOD = 0x21;			//T0与T1一起赋值
	TH1 = 0xfd;				//设置9600波特率
	TL1 = 0xfd;
	TR1 = 1;					// 启动定时器1
	
	SCON = 0x50;			//8位UART
	AUXR = 0x00;			//辅助寄存器
	
	ES = 1;						//使能串口中断
	EA = 1;						//使能总中断
}
/*=================串口中断服务函数====================
功能:接收上位机所发送的字符
=======================================================*/
void ServiceUart() interrupt 4
{
	if(RI == 1)
	{
		command = SBUF;		//½«½ÓÊÕµ½µÄÊý¾Ý±£´æµ½command±äÁ¿
		RI = 0;						//½«½ÓÊÕÍê³É±êÖ¾RIÇå0
	}
}
/*=================串口服务函数====================
功能:接收上位机发送的数据并保持在command里
参数:无
=======================================================*/
void SendByte(unsigned char dat)
{
	SBUF = dat;
	while(TI == 0);
	TI = 0;
}
 
void SendString(unsigned char *str)
{
	while(*str != '\0')
	{
		SendByte(*str++);
	}
}
 
/*===============串口信息接收执行函数==================
功能:接收上位机消息,进行灯光控制
参数:无
=======================================================*/
void ExecuteCommand()
{
	if(command != 0x00)							//接收的消息不为空
	{
		switch(command & 0xf0)				    //将命令类型取出
		{
			case 0xa0:									//远程控制灯光
				SelectHC573(4);
				stat_led = (stat_led | 0x0f) & (~command | 0xf0);
				P0 = stat_led;
				SelectHC573(0);
				command = 0x00;
			break;
			
			case 0xb0:									//读取系统运行时间
				SendByte((t_h / 10 << 4) | (t_h % 10));
				SendByte((t_m / 10 << 4) | (t_m % 10));
				SendByte((t_s / 10 << 4) | (t_s % 10));
				command = 0x00;
			break;
		}
	}
}

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

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

相关文章

java+springboot笔记2023005--java基础

Java语言是纯粹的面向对象的程序设计语言&#xff0c;主要表现为Java完全支持面向对象的三种基本特征&#xff1a;继承、封装和多态。Java语言完全以对象为中心&#xff0c;Java程序的最小程序单位是类&#xff0c;整个Java程序由一个一个的类组成。 封装指的是将对象的 实现细…

【链表】无头单向非循环链表

本节知识所需代码已同步到gitee --》单链表关注作者&#xff0c;持续阅读作者的文章&#xff0c;学习更多知识&#xff01; https://blog.csdn.net/weixin_53306029?spm1001.2014.3001.5343 单链表顺序表的问题及思考链表链表的概念及结构链表的分类无头单向非循环链表初始化链…

windows默认文件(桌面、下载、文档等)设置为C盘根路径后怎么修改回去

桌面、下载、文档等设置为C盘根路径后怎么修改回去1.问题2.解决办法2.1.按Win R调出运行窗口&#xff0c;输入regedit并按回车。2.2.在弹出的注册表窗口里&#xff0c;打开下面路径计算机\HKEY_CURRENT_USER\SOFTWARE\Microsoft\Windows\CurrentVersion\Explorer\User Shell F…

1.15 SPI数码管实验

一.SPI总线 SPI是全双工三/四总线制串行总线&#xff0c;支持多主机多从机模式&#xff0c;常用单主机多从机模式 数据传输可以先传输高位也可以先传输低位。 四线&#xff08;单主机多从机&#xff09;&#xff1a; MOSI&#xff1a;主机输出&#xff0c;从机输入 …

9. 垃圾收集器与内存分配策略

整体思路 先考虑3个问题 哪些内存需要收集 堆和方法区需要收集&#xff1b;程序计数器、虚拟机栈、本地方法栈都不需要做垃圾回收&#xff08;按照其功能很容易理解&#xff09; 什么时候收集 对象已死。引申出另一个问题&#xff0c;怎么判断对象已死呢&#xff1f;当程序内…

外部链接<a>

创建外部链接 HTML 通过使用 标签在 HTML 中创建链接。 注意&#xff1a;移除 target“_blank” 属性避免点击链接会打开新的元素页。 使用a元素实现页面内跳转 a元素也可以用在网页内不同区域的跳转。 设置a元素的 href 属性值为井号#加上想跳转区域对应的id属性值&…

ASP.NET Core 3.1系列(28)——ASP.NET Core中使用Autofac替换内置IoC容器

1、前言 前面的博客主要介绍了一些Autofac的使用方法&#xff0c;示例代码都是基于控制台程序。本文就来介绍一下如何在ASP.NET Core中使用Autofac代替内置的IoC容器。 2、创建接口和类 这里搭建了一个简易的项目&#xff0c;如下图所示&#xff1a; Service层代码如下&…

长安汽车推动新伙伴变革重塑供应链模式发布长安智电iDD技术

1月12日&#xff0c;以“携手勇进一路有你”为主题的2023长安汽车全球伙伴大会在重庆大剧院举行。此次大会&#xff0c;是长安汽车总结过往生产经营良好态势&#xff0c;研判行业未来发展趋势&#xff0c;发布最新企业发展战略&#xff0c;与全球合作伙伴共谋新未来&#xff0c…

【JavaEE】网络编程基础之Socket套接字

✨哈喽&#xff0c;进来的小伙伴们&#xff0c;你们好耶&#xff01;✨ &#x1f6f0;️&#x1f6f0;️系列专栏:【JavaEE】 ✈️✈️本篇内容:网络编程基础之Socket套接字。 &#x1f680;&#x1f680;代码存放仓库gitee&#xff1a;JavaEE初阶代码存放&#xff01; ⛵⛵作者…

机器学习:公式推导与代码实现-概率模型

最大信息熵模型 根据最大信息熵原理,信息熵最大时得到的模型是最优模型,即最大信息熵模型。 最大信息熵原理 信息论的开创者香农将信息的不确定程度称为熵,为了与热力学中熵的概念区分,这种信息的不确定程度又称信息熵。 最大信息熵原理认为在所有可能的概率模型中,熵…

【Python从入门到进阶】4、pycharm的安装及使用

接上篇《3、运行python代码》 上一篇我们学习了如何使用终端和执行文件运行python代码&#xff0c;本篇我们来学习python编程工具pycharm的安装及基本使用。 一、IDE的概念 上一篇我们介绍了使用命令行指令执行和文件编译的方法进行python代码的解释执行&#xff0c;但是仍然…

总之2022,我的研发、直播、软文触达13W+人的成果打包拿走,展望2023一起加油

导读 | 2022年勇哥算是正是进入写作圈&#xff0c;在小伙伴们的支持下&#xff0c;勇哥也是每日每夜的肝&#xff0c;真心和小伙伴们分享技术前沿路上的系列故事&#xff0c;大家相互鼓励与支持&#xff0c;勇哥也是收获满满&#xff01;现在勇哥通过这边文章整理一下本年度&am…

重装系统win11服务器未响应怎么修复操作

最近网友问小编win11服务器未响应怎么修复?最近有用户询问这个问题&#xff0c;在使用电脑的时候遇到了服务器无响应的情况&#xff0c;今天小编来教大家win11服务器未响应怎么修复操作&#xff0c;希望能帮到各位。 工具/原料&#xff1a; 系统版本&#xff1a;Windows11 品…

Koa 真解

1. 前言 昨天花费了比较多的时间将Koa的源码阅读了一遍&#xff0c;主要是项目中用到了Koa&#xff0c;为了做的更加得心应手所以先将源码看一下&#xff0c;总体上源码还是非常简单的&#xff0c;没啥难度。一方面为了总结另一方面也是为了不太看懂源码的同学们&#xff0c;今…

代码审计-7 ThinkPHP框架代码审计

ThinkPHP框架目录 applocation&#xff1a;此目录为应用目录&#xff0c;网站主要的文件控制器都放在applocation目录下 view&#xff1a;此目录在applocation下&#xff0c;为视图层 extend&#xff1a;为扩展类库目录 public&#xff1a;为网站对外访问目录&#xff0c;也就…

汽车路径尽头放一个点图像验证

文章目录前言一.图片二.大致思路2.1 小车位置识别2.2 采用轮廓算法得到路径的坐标2.3 采用断点续连的方法&#xff0c;将轮廓算法得到点组成直线&#xff0c;并寻找到最后的坐标三 缺陷四.如果大佬有其他的好的方法欢迎大佬们留言交流前言 提示&#xff1a;文章写完后&#xf…

坑多路难走,学数据分析转行前要知道培训机构不会说的事情

想要转行做数据分析师&#xff1f;那就要做好迎接坑多路难走的准备。虽然培训机构可以教你如何使用工具和算法&#xff0c;但它们很少会告诉你真正的行业现状。在这个竞争激烈的领域中&#xff0c;需要知道的不仅仅是如何处理数据&#xff0c;还有如何在企业中应用它。 跟着我…

CMMI之配置管理

配置管理&#xff08;Configuration Management, CM&#xff09;的目的是通过执行版本控制、变更控制等规程&#xff0c;以及使用配置管理软件&#xff0c;来保证所有配置项的完整性和可跟踪性。配置管理是对工作成果的一种有效保护。配置管理过程域是SPP模型的重要组成部分。本…

42. 【农产品溯源项目前后端Demo】后端-区块链连接服务

本节介绍后端代码是如何与区块链网络连接的。 1.在后端代码里fabric包 负责与区块链网络连接,并发送交易。 2.fabric.Const文件 定义 区块链网络拓扑结构,请查看注释。 public final class Const {//区块链网络中organizations的配置目录,从配置文件读取证书目录public stat…

【JavaEE】单例模式如何保证在多线程环境下线程安全高可用?

文章目录1 单例模式回顾2 饿汉式单例模式的实现3 懒汉式单例模式的实现4 单例模式的线程安全问题分析5 线程安全的懒汉式实现6 总结1 单例模式回顾 单例模式是设计模式的一种。而设计模式就是针对我们实际开发中写代码所遇到的不同场景所设立的解决方案。在笔者JavaSE阶段的文章…