基于STM32的汽车仪表系统设计

news2024/9/24 0:56:19

收藏和点赞,您的关注是我创作的动力

文章目录

    • 概要
  • 一、方案设计
    • 1.1 总体方案论证
    • 1.2 项目总体设计
  • 二、软件设计
    • 3.1 主程序设计
  • 三、软件设计
    • 3.3 emWin图形界面实现
    • 实物
    • 附录2 源程序清单
  • 四、 结论
  • 五、 文章目录

概要

  本次课题基于STM32F407微型控制器以及CAN总线通信技术,设计一款新型全液晶汽车仪表。相比于传统的机械式指针仪表,本设计的汽车仪表具有简单的接线方式,快速的模块之间通讯以及全液晶显示等特点。同时,该课题中采用emWin技术进行LCD液晶显示屏的设计,具有更直观美化的人机交互界面,而且由于采用了CAN总线通信方式,元器件与控制元件(ECU)之间信息传递性将会更好。本次课题,采用CAN分析仪开发测试工具,通过定义好相关模拟变量,模拟实际汽车中的情况输入CAN信号报文并利用Simulink建模进行汽车仪表灯的逻辑处理。同时将FreeRTOS实时操作系统移植到STM32F407上,利用STM32芯片输入输出信号,进而达到点亮汽车仪表的目的。
通过软件与硬件方面的调试,该课题达到了预期研究要求,证明了课题技术上的可行性以及延展性。

关键词:汽车仪表; CAN总线; STM32F407; Simulink建模; FreeRTOS

一、方案设计

1.1 总体方案论证

本课题对于实现汽车仪表系统提出如下两套设计方案。
方案一:
本设计采用通过串口与按键的方式来进行汽车仪表的实现。该方式通过使用串口调试工具,在PC端向STM32芯片发送指令,经过STM32的识别后,输出到显示模块上。按键控制则是通过改变STM32芯片I/O口的高低电平,实现某个特定的仪表指示功能的点亮与熄灭。该方案分为硬件模块以及软件设计两个模块。其中硬件模块包括:主控芯片、按键控制电路、蜂鸣器报警电路、指针电机电路以及LED显示电路。软件方面采用了Keil5编程软件向STM32芯片烧写代码程序。
其中电源电路包括STM32的最小系统以及下载电路;按键电路主要负责系统的启动/关闭,以及相关指示灯的点亮/熄灭;蜂鸣器电路是根据STM32的输出信号,当某些报警条件触发时,蜂鸣器就会工作;电机电路采用伺服电机进行模块的控制,主要负责车速表的指针转动,转速表的指针转动等;LED显示电路则是根据STM32的输出信号,点亮对应的指示灯或熄灭对应的指示灯。
该方案的弊端主要为,机械式的仪表指针过于传统化,人机交互界面不够美观且智能化。同时,由于现代汽车仪表包含多种功能,需要大量的仪表指示灯与驾驶员进行交互。在本方案中采用的LED显示灯所呈现的信息不够生动、具体,而且需要大量的LED去表达对应的仪表指示灯,容易造成资源的浪费,且给项目的布线和通讯带来很大的麻烦。另一方面,由于项目存在大量的仪表模块,单一的点对点导线通讯很难完成高效的通讯实现,会对项目的实现造成干扰。
方案二:
本设计采用STM32芯片与CAN总线结合的方式实现汽车仪表。通过CAN分析仪发送报文,STM32处理输入输出报文信号,根据相应的条件控制显示模块与蜂鸣器模块。为了更直观的显示,在本设计中也增加了按键的硬线控制模块,通过按键控制某些特定的仪表灯。本设计主要分为硬件设计与软件设计。硬件模块包括:电源电路,蜂鸣器电路,按键电路以及LCD显示电路。软件设计主要由Keil5与Matlab来实现。
在本设计中,在LCD显示模块上,会采用软件烧写的方式,实现一款全液晶的仪表显示屏以取代电机模块与LED模块。相比于机械指针的方式,全液晶显示屏具有更美观,更直观的人机交互界面,同时节省了大量的LED以及布线需求。在通信的传递上,采用新兴的CAN总线传递方式,相比于传动的导线通信,CAN总线具有更高效,更稳定且更安全的通信方式。同时,在本次设计中,将会移植FreeRTOS实时操作系统到STM32芯片上。该方法可以实现多进程任务,可以在更好的处理不同情况下的仪表条件。
因此,采用方案二的汽车仪表系统更符合我们的实际需求,更贴切现代发展,该方案操作性高,维护性好,具有良好的安全性与实用性。因此,本设计采用方案二。

1.2 项目总体设计

本项目基于STM32F407设计的汽车仪表系统由:主控芯片,CAN通讯模块,按键模块,LCD显示模块和报警模块组成。STM32主控制芯片负责在接收到CAN通信传来的信号或者按键按下时的系统任务调度,经过主控芯片处理后,会输送到LCD显示模块和报警模块,执行点亮或熄灭相关指示灯,蜂鸣器警报,同步水温表,车速表等操作。系统功能框图如图1.1所示。

在这里插入图片描述

图1.1 系统功能框图

该项目分为两种控制方式:CAN总线通信以及按键硬线通信。通过使用CAN收发器实时发送CAN报文给STM32芯片,STM32芯片会判断是否满足相关条件,执行点亮/闪烁/熄灭相关仪表灯或报警。由于在STM32中移植FreeRTOS实时操作系统,会在一个循环周期内不停检测是否接收到CAN报文,执行多个任务调度,实现多个仪表灯的控制。按键控制则是通过定义好的I/O口与仪表灯,当按键按下或取消时,仪表灯和报警会有对应的显示。至此为该项目的流程与功能。

二、软件设计

3.1 主程序设计

本课题设计的主程序流程如图3.1所示,开机后会初始化液晶显示屏,内部时钟以及I/O口。在FreeRTOS里建立两个任务,分别为主程序任务以及显示任务(主程序任务优先级大于显示任务)。主程序任务会根据内部时钟,不停地循环。当STM32收到信息或按键按下,会判断是否有效。如若无效,不执行任何操作,继续循环。如若有效,会切换到显示任务中,根据逻辑,输出对应的信号,更新LCD液晶显示屏上的信息或蜂鸣器鸣响。
在这里插入图片描述

图3.1 程序主流程图

三、软件设计

3.3 emWin图形界面实现

为了完善本设计对仪表仪器人机交互界面操作的人性化、智能化的需求,本设计引用了emWin在stm32嵌入式设计,使用了GUIBuilder作为一种LCD界面图形可视化程序的设计方法,最终驱动硬件电路完成LCD显示[15]。在TaskDisplay中,利用Bmpcvt.exe软件可将png格式的图片转化为16进制的C代码格式。在APP模块中,调用GUIBuilder的API函数“GUI_DrawBitmap”,即可实现图片的显示。项目部分源码如图3.5所示:
在这里插入图片描述

图3.5 emWin实现
emWin可以在操作系统下的多任务中工作。它具有模块化的特点,采用分层结构。emWin总共包括4层,每层可以单独使用。包括第一层:LCD驱动器;第二层:图形库;第三层:插件库;第四层:窗口管理器[16]。emWin是以C语言的形式实现,通过对第一层的修改,就可应用到项目中。emWin模块流程图如3.6所示:

在这里插入图片描述

图3.6 emWin流程图
在汽车仪表的图形化界面设计中,最为重要的就是仪表指针转动的设计。仪表指针需要根据STM32收到的CAN报文,来在图形界面中有相应的显示。为了使指针的精度精准,需要用量角器测出仪表盘的数据刻度,在代码中进行算法优化。以车速表为例,如图3.7所示:
在这里插入图片描述

图3.7 车速表概念图
如上图所示,将该仪表盘看做一个在坐标轴上的圆形,从X轴起始到0刻度大约为225度,到170刻度大约为45度。因此该车速表可以看做一个半径为1的270度圆,既1.25×3.14+0.25×3.14。当CAN报文传输进20KM/h的值时,只需让指针指向约195度的位置,既1.16×3.14,就可以实现仪表指针的精准转动。具体代码如图3.8所示:
在这里插入图片描述

图3.8 指针算法
具体的数据会在调试中,根据实际情况的变化而改变以到达最小误差的效果。

实物

在这里插入图片描述

附录2 源程序清单

#include "GUI.h"
#include "JPGResource.h"
#include "displayapp.h"
#include "sys.h"
#include "delay.h"
#include "key.h"
#include "Beep.h"

uint16_t gEngCoolantValue = 0;
uint16_t gFuelResistanceValue = 0;
uint16_t gESCVehSpeed = 0;								//0-170km/h
uint32_t gEMSEngSpd = 0;									//0-8000
uint32_t gODOMeter = 0;
uint8_t gturnleft = 0;
uint8_t gturnright = 0;
uint32_t flag = 0;
uint8_t gAir = 0;
uint8_t gseatbelt = 0;
uint8_t gseatbelt1 = 0;
uint8_t gABSwarning = 0;
uint8_t gPark = 0;
uint8_t gposition = 0;

static const GUI_POINT aPointer[] = {
	{ 0, 10 },
	{ 150, 0 },
	{ 0, -10 },
	{ -20, 0 },
};
static const GUI_POINT aSmallPointer[] = {
	{ 0, 5 },
	{ 40, 0 },
	{ 0, -5 },
	{ -10, 0 },
};

static GUI_POINT aPointerHiRes[countof(aPointer)];
static GUI_POINT aSmallPointerHiRes[countof(aSmallPointer)];

typedef struct {
GUI_AUTODEV_INFO AutoInfo;
GUI_POINT aPoints[countof(aPointer)];
GUI_POINT aSmallPoints[countof(aSmallPointer)];
int Factor;
}PARAMPolygon;

#define HMI_POS_Y	25

static void DrawSpeed(void * p) 
{
	int posX = 25, posY = HMI_POS_Y;
	PARAMPolygon * pParam = (PARAMPolygon *)p;
	if (pParam->AutoInfo.DrawFixed) {
	GUI_ClearRect(posX, posY, bmspeed.XSize + posX, bmspeed.YSize + posY);
	GUI_DrawBitmap(&bmspeed,posX,posY);
	}
	GUI_AA_FillPolygon(pParam->aPoints, countof(aPointer), (posX + 160)*pParam->Factor, (posY + 160)* pParam->Factor );//车速针
	GUI_AA_FillPolygon(pParam->aSmallPoints, countof(aSmallPointer), (posX + 170)*pParam->Factor, (posY + 305)* pParam->Factor);//油表针
}

static void DrawVelocity(void * p) 
{
	int posX = 425, posY = HMI_POS_Y;
	PARAMPolygon * pParam = (PARAMPolygon *)p;
	if (pParam->AutoInfo.DrawFixed) {
	GUI_ClearRect(posX, posY, bmvelocity.XSize + posX, bmvelocity.YSize + posY);
	GUI_DrawBitmap(&bmvelocity,posX,posY);
	}
	GUI_AA_FillPolygon(pParam->aPoints, countof(aPointer), posX + 160, posY + 160);//转速针
	GUI_AA_FillPolygon(pParam->aSmallPoints, countof(aSmallPointer), posX + 170, posY + 305);//水温
}

void keyBeam()
{
	u8 key;
		key=KEY_Scan(0);
		if(key)
		{						   
			if(key == WKUP_PRES)
			{				 
				GUI_DrawBitmap(&bmHigh_Beam,610,380);
			}
			else
			{
				GUI_ClearRect(610, 380, bmHigh_Beam.XSize + 610, bmHigh_Beam.YSize + 380);
			}
			if(key == KEY0_PRES)
			{
				GUI_DrawBitmap(&bmlow_beam,530,380);	
			}
			else
			{
				GUI_ClearRect(530, 380, bmlow_beam.XSize + 530, bmlow_beam.YSize + 380);
			}
		}else delay_ms(10);
}

void show()
{
	if( gturnleft == 1)
		{
			if( flag == 1)
				{
					GUI_DrawBitmap(&bmTurn_left,255,380);
					BEEP = 1;
				  delay_ms(100);
					BEEP = 0;
				}
			else
				{
					GUI_ClearRect(255, 380, bmTurn_left.XSize + 255, bmTurn_left.YSize + 380);
				}
		}
	if( gturnright == 1)
		{
			if(	flag == 1)
			{
				GUI_DrawBitmap(&bmTurn_right,445,380);
				BEEP = 1;
				delay_ms(100);
				BEEP = 0;
			}
			else
				{
					GUI_ClearRect(445, 380, bmTurn_right.XSize + 445, bmTurn_right.YSize + 380);
				}
		}
	if( gABSwarning == 1)
	{
		GUI_DrawBitmap(&bmABS_warning,310,5);
	}
	else
	{
		GUI_ClearRect(310, 5, bmABS_warning.XSize + 310, bmABS_warning.YSize + 5);
	}
	if( gPark == 1)
	{
		static int t = 0;
		GUI_DrawBitmap(&bmParkingIndication_green,400,10);
		if( t == 0)
		{
			BEEP = 1;
			delay_ms(100);
			BEEP = 0;
			delay_ms(100);
			BEEP = 1;
			delay_ms(100);
			BEEP = 0;
			t = 1;
		}
	}
	else
	{
		GUI_ClearRect(400, 10, bmParkingIndication_green.XSize + 400, bmParkingIndication_green.YSize + 10);
	}
	if( gposition == 1)
	{
		GUI_DrawBitmap(&bmPosition_lamp,690,380);
	}
	else
	{
		GUI_ClearRect(690, 380, bmPosition_lamp.XSize + 690, bmPosition_lamp.YSize + 380);
	}
	if( gAir == 1)
		{
				GUI_DrawBitmap(&bmAirbag_warning,35,380);
		}
		else
		{
			GUI_ClearRect(35, 380, bmAirbag_warning.XSize + 35, bmAirbag_warning.YSize + 380);
		}
		if( gseatbelt == 1)
		{	
			GUI_DrawBitmap(&bmseatblet,105,380);//显示
			BEEP = 1;
			delay_ms(50);
			BEEP = 0;
			delay_ms(50);
			BEEP = 1;
			delay_ms(50);
			BEEP = 0;
			delay_ms(1000);
		}
		else
		{
			GUI_ClearRect(105, 380, bmseatblet.XSize + 105, bmseatblet.YSize + 380);//清除
		}
		if( gseatbelt1 == 1)
		{	
			GUI_DrawBitmap(&bmseatblet_1,185,380);//显示
			BEEP = 1;
			delay_ms(50);
			BEEP = 0;
			delay_ms(50);
			BEEP = 1;
			delay_ms(50);
			BEEP = 0;
			delay_ms(1000);
		}
		else
		{
			GUI_ClearRect(185, 380, bmseatblet_1.XSize + 185, bmseatblet_1.YSize + 380);//清除
		}
}

#define PI 3.1415
float GetAngleSpeed(uint32_t val)
{
	float frange = 1.22 * PI + 0.22 * PI;//车速表
	float leftRange = 1.28 * PI;			
	uint16_t maxSpeed = 170, minSpeed = 0;
	float temp;
	if ( val > maxSpeed )val = 170;
	temp = (float)val / 170 * (frange);
	if( temp >0.5 * PI)
	{
		if ( temp > 1.22 * PI )
		{
				temp = 2 * PI - ( temp - 1.22 * PI);
		}
		else
		{
				temp = 1.22 * PI - temp;
		}
	}
	else
	{
			temp = leftRange - temp;
	}
	return temp;
}

float GetAngleEngSpeed(uint32_t val)
{
	float frange = 1.22 * PI + 0.19 * PI;
	float leftRange = 1.21 * PI;
	uint16_t maxSpeed = 8000, minSpeed = 0;
	float temp;
	if ( val > maxSpeed )val = 8000;
	temp = (float)val / (maxSpeed - minSpeed) * (frange);
	
	if ( temp > 1.21 * PI )
	{
		temp = 2 * PI - (temp - 1.21 * PI);
	}
	else
	{
		temp = leftRange - temp;
	}
	return temp;
}

float GetAngleTempature(uint32_t val)
{
	float frange = 1.25 * PI - 0.3 * PI;
	float leftRange = 1.25 * PI;
	uint16_t maxTempature = 120, minTempature = 0x00;
	float temp;
	if ( val > maxTempature )val = 120;
	temp = (float)val / (maxTempature - minTempature) * (frange);
	temp = leftRange - temp;
	return temp;
}

float GetAngleFuel(uint32_t val)
{
	float frange = 0.93 * PI - 0.07 * PI;
	float leftRange = 0.93 * PI;
	uint16_t maxFuel = 0x0029, minFuel = 0x00;
	float temp;
	if ( val > maxFuel )val = 0x0029;
	temp = (float)val / (maxFuel - minFuel) * (frange);
	temp = leftRange - temp;
	return temp;
}


void HMIDisplay(void) 
{
  GUI_AUTODEV  aAuto[10];
	PARAMPolygon Param;
	int i;
	Param.Factor = 3;

	for (i = 0; i < countof(aAuto); i++) 
	{
		GUI_MEMDEV_CreateAuto(&aAuto[i]);
	}

	for (i = 0; i < countof(aPointer); i++) 
	{
		aPointerHiRes[i].x = aPointer[i].x * Param.Factor;
		aPointerHiRes[i].y = aPointer[i].y * Param.Factor;
	}
	
	for (i = 0; i < countof(aSmallPointer); i++) 
	{
		aSmallPointerHiRes[i].x = aSmallPointer[i].x * Param.Factor;
		aSmallPointerHiRes[i].y = aSmallPointer[i].y * Param.Factor;
	}
	
	
	GUI_AA_SetFactor(Param.Factor); 
	
	while(1) 
	{
		keyBeam();
		show();
		for (i = 0; i < 10; i++) 
		{								

			GUI_AA_EnableHiRes();
		
			GUI_RotatePolygon(Param.aPoints, aPointerHiRes, countof(aPointer), GetAngleSpeed(gESCVehSpeed));//速度
			GUI_RotatePolygon(Param.aSmallPoints, aSmallPointerHiRes, countof(aSmallPointer), GetAngleFuel(gFuelResistanceValue));//油耗
			GUI_MEMDEV_DrawAuto(&aAuto[0], &Param.AutoInfo, DrawSpeed, &Param);
			
			GUI_AA_DisableHiRes();
			GUI_RotatePolygon(Param.aPoints, aPointer, countof(aPointer), GetAngleEngSpeed(gEMSEngSpd));//转速
			GUI_RotatePolygon(Param.aSmallPoints, aSmallPointer, countof(aSmallPointer), GetAngleTempature(gEngCoolantValue));//水温
			GUI_MEMDEV_DrawAuto(&aAuto[1], &Param.AutoInfo, DrawVelocity, &Param);
			
			GUI_SetFont(GUI_FONT_D24X32);
			GUI_SetTextAlign(GUI_TA_RIGHT);
			GUI_GotoXY(425,405);
			GUI_DispDecMin(gODOMeter);
			GUI_Delay(20);
		} 
	}
}



四、 结论

警灯”,“当前车速80KM/S”等,经过CAN收发器的接收传递给STM32F407,STM32F407经过逻辑运算,判断该信息是否符合显示模块的条件,进而驱动LCD显示屏以及蜂鸣器模块。LCD显示屏就会根据emWin指令,在屏幕指定位置呈现图形,包括不同颜色,是否闪烁等情况。当再次收到STM32指令时,也会进一步决定是否取消报警或更换报警等情况。既此时为一个周期的流程,该流程在整个汽车仪表系统中为10ms一次,从上电开始。
采用CAN总线通信的汽车仪表系统,通信效果得到很大的增强,抗干扰能力也有显著的提高。而LCD液晶显示屏的改进,也使得人机交互界面更加的美观,令人舒适。由于该项目仅为模拟通信实验,具体实验数据还有待考证,包括MCU的处理效率,多MCU间的CAN通信,液晶显示屏的动画效果等。但由此可见基于CAN总线通信的液晶汽车仪表,在未来具有很大的期望空间。

五、 文章目录

目 录
摘 要 I
Abstract II
引 言 1
1 方案设计 3
1.1 总体方案论证 3
1.2 项目总体设计 4
2 项目硬件设计 6
2.1 单片机 6
2.1.1 ARM Cortex-M4内核 6
2.1.2 STM32F407ZGT6芯片 6
2.2最小系统模块 8
2.3 LCD显示电路 9
2.4 CAN通信电路 11
2.5蜂鸣器以及按键电路 12
3 软件设计 14
3.1 主程序流程 14
3.2 FreeRTOS移植 15
3.3 emWin图形界面实现 16
3.4 Simulink建模处理 19
4 项目调试 21
4.1 软件调试 21
4.1 重点问题及解决 22
结 论 24
参考文献 25
附录:程序主函数 27
致 谢 36

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

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

相关文章

智能决策:数字孪生的商业洞察

数字孪生在企业管理中的应用是一项重要的技术趋势&#xff0c;它为企业提供了强大的工具&#xff0c;以数字化的方式模拟和管理其物理资产、流程和运营。本文将探讨数字孪生在企业管理中的关键应用领域&#xff0c;以及它对企业的益处。 1. 制造业优化 数字孪生可以在制造业中…

RabbitMQ-死信交换机和死信队列

1. 简介 DLX: Dead-Letter-Exchange 死信交换器&#xff0c;死信邮箱 2.代码示例 Configuration public class RabbitConfig {final static String exchangeNormalName "exchange.dlx.normal";final static String queueNormalName "queue.dlx.normal"…

springsecurity学习笔记-未完

目录 前言 一、概念 1.什么是springsecurity 2.对比shiro 二、开始项目 1.建立一个空项目&#xff0c;建立module&#xff0c;引入相关依赖 2.启动项目&#xff0c;访问项目 3.自定义密码 总结 前言 记录一下学习springsecurity的过程 开发环境&#xff1a;IDEA 一、概念 1.…

shell脚本的编写(输入、输出、变量、数组等的使用规范及实例)

1.shell中变量的定义 使用变量的值&#xff1a; 例子&#xff1a; 2.外部传参/位置变量 例子&#xff1a; 3.输出---echo 4.输入---read 5.命令置换符 作用:把指令的运行结果赋值给变量 6.数组--shell支持稀疏数组

计算机视觉的相机选型

#你一般什么时候会用到GPT?# 目前市面上的工业相机大多是基于CCD&#xff08;ChargeCoupled Device&#xff09;或CMOS&#xff08;Complementary Metal Oxide Semiconductor&#xff09;芯片的相机。一般CCD制造工艺更加复杂&#xff0c;也会更贵一点&#xff01; 1、CCD工…

请求分页中的内存分配

1.最小物理块数的确定 这里所说的最小物理块数&#xff0c;是指能保证进程正常运行所需的最小物理块数。当系统为进程分配的物理块数少于此值时&#xff0c;进程将无法运行。 2.内存分配策略 1&#xff09;内存分配策略 固定分配是指为每个进程分配一固定页数的内存空间&am…

支持自动生成API文档 Apipost 真香

在数字化时代&#xff0c;API已经成为了应用程序之间进行通信的关键桥梁。随着API的普及和复杂性的增加&#xff0c;API研发和管理也面临着越来越多的挑战。为了更好地应对这些挑战&#xff0c;Apipost提供了一整套API研发工具&#xff0c;包括API设计、API调试、API文档和API自…

碳排放数据,各地区的(直辖市数据细分到区县),含shp和xlsx格式,带符号化

这两天推了道路相关的数据&#xff0c;道路线路、客运飞机场、航空、地铁、火车站点等等交通出行类的数据之前都已发过&#xff0c;需要的可以自己翻一翻。 交通运输行业还比较关注的碳排放数据&#xff0c;也整理出来了&#xff0c;有需要的自取。 数据地址&#xff1a; 全…

政务可视化 玫瑰图和柱折混合图

安装echarts时&#xff0c;需进入到vue-demo的目录下 与第二章操作步骤相同 删除全部默认效果 将上述60像素删除&#xff0c;设置整个背景宽&#xff0c;高等 设置标题 设置图表结构&#xff08;左右两个盒子&#xff09; 设置图表边框&#xff0c;宽&#xff0c;高&#xff0…

Peter算法小课堂—归并排序

位运算 << 这个符号相当于将一个数二进制往左移动几位&#xff0c;如(100110)2<<1(001100)2。相当于乘以2的k次方 >> 这个符号相当于将一个数二进制往右移动几位&#xff0c;如(100110)2<<1(0100110)2。相当于除以2的k次方 归并排序 先看一个视频…

token正确不报错,token失效后却出现报跨域错误

1.今天在使用koajs开发项目时&#xff0c;突然发现前端配置axios的response获取不到后端定义的token失效内容了&#xff0c;取而代之的是出现了跨域的错误。 2. 我马上去查找koajs的跨域中间件配置&#xff0c;发现配置完好cors&#xff0c;token正确时&#xff0c;接口正常访问…

code too large

描述&#xff1a;比较尴尬&#xff0c;一个方法的代码接近10000行了&#xff0c;部署服务器的时候提示(java :code[255,21] too large),提示代码过长&#xff0c;无法运行。 查看了一下百度&#xff1a;解决的思路 JVM规范&#xff1a;「类或接口可以声明的字段数量限制在 655…

水声功率放大器的应用场景是什么

水声功率放大器是一种专门用于水声信号处理和传输的设备&#xff0c;通过放大水声信号的功率&#xff0c;以实现远距离传播和提高信号的清晰度和可辨识度。下面是关于水声功率放大器应用场景的详细解释&#xff1a; 水声通信&#xff1a;水声通信是一种在水下进行声波传输的技术…

电脑如何激活windows

当我们电脑出现如下图&#xff1a; 显示需要激活windows时&#xff0c;操作如下。 1、桌面-新建-文本文档 2、将文档命名为&#xff08;激活windows.bat&#xff09;把原有文档中的后缀.txt去掉 3、点击右键&#xff0c;选择编辑输入代码 slmgr/skms kms.03k.org slmgr/ato4、…

logback-classic包中ThrowableProxy递归缺陷StackOverflowError解析

logback-classic&#xff08;<1.2.12版本&#xff09;ThrowableProxy类中存在递归缺陷&#xff0c;会导致java.lang.StackOverflowError。改缺陷在1.2.12以上版本(包含该版本)中已修复。 如何复现&#xff1a; 两个异常彼此设置casue&#xff1a; 运行后报以下错误 以上写…

Rust 模块系统

文章目录 模块系统crate包cargo 创建库库的使用 模块系统 Rust的{模块系统|the module system}&#xff0c;包括&#xff1a; * 包&#xff08;Packages&#xff09;&#xff1a; Cargo 的一个功能&#xff0c;它允许你构建、测试和分享 crate。 * Crates &#xff1a;一个模…

【Uva】10976-Fractions Again?!

1、题目 2、题意 输入正整数 k k k&#xff0c;找到所有正整数 x ≥ y x \ge y x≥y&#xff0c;使得 1 k 1 x 1 y \frac{1}{k} \frac{1}{x} \frac{1}{y} k1​x1​y1​。 3、分析 既然要求找出所有的 x , y x,y x,y&#xff0c;枚举对象自然是 x , y x,y x,y了。可…

有用过成绩查询系统的老师吗?

是不是有时候觉得手动查询成绩是一件超级繁琐的事情&#xff1f;有了这个成绩查询系统&#xff0c;你就可以告别手动时代啦&#xff01; 先来了解一下什么是成绩查询系统。成绩查询系统是一种可以自动查询学生成绩的系统。通过这个系统&#xff0c;学生可以输入自己的学号或姓名…

使用管理员其权限打开cmd,如何切换到其他磁盘

问题描述&#xff1a; 切换到 O:\BaiduSyncdisk\develope\mysql-8.0.31-winx64 &#xff0c;直接使用cd命令切换失败。 原因是因为&#xff0c;在使用管理员身份打开cmd的时候&#xff0c;只能切换到当前盘符下的目录&#xff0c;而不能切换到其他盘符下的目录。 解决方案&am…

Android原生项目集成uniMPSDK(Uniapp)遇到的报错总结

uni小程s序SDK 集成到Android原生项目:老项目中用到的库较多&#xff0c;会出现几种冲突问题&#xff0c;总结如下&#xff1a; 报错1&#xff1a; Execution failed for task :app:processDebugManifest. > Manifest merger failed with multiple errors, see logs Andro…