当前位置: 首页 > news >正文

深入解析嵌入式Linux系统架构:从Bootloader到用户空间


B站视频链接,请多多关注本人B站
📌 Yocto项目实战教程:第二章 视频讲解


在这里插入图片描述

目录

  • 第2章 Linux系统架构
    • 2.1 GNU/Linux
    • 2.2 Bootloader
    • 2.3 内核空间
    • 2.4 用户空间
  • 总结

第2章 Linux系统架构 {#linux系统架构}

嵌入式Linux系统是Linux内核的精简版本,广泛应用于物联网设备、工业控制、消费电子等领域。其核心架构由**内核空间(Kernel Space)用户空间(User Space)**构成,两者通过系统调用接口交互。本章将深入分析其关键组件,包括引导加载程序(Bootloader)、内核、文件系统及用户空间组件,为后续学习Yocto项目奠定基础。

系统架构总览

Linux系统的核心设计遵循权限隔离原则

  • 内核空间:拥有最高权限,直接管理硬件资源(如CPU、内存、设备驱动)。

  • 用户空间:运行用户程序,通过系统调用访问内核功能,权限隔离保障系统安全。

    在这里插入图片描述

图2-1:Linux系统架构示意图


2.1 GNU/Linux

2.1.1 GNU/Linux概述

GNU项目始于1984年,旨在构建完全自由的操作系统。然而,其最初的内核GNU Hurd因开发缓慢和技术复杂性未能普及。1991年,Linus Torvalds开发了Linux内核,其快速发展和高度兼容性使其成为GNU项目的理想选择。最终,GNU/Linux操作系统诞生,成为现代开源生态的基石。

2.1.2 Linux系统架构

Linux架构分为两部分:

  1. 内核空间
    • 功能:进程调度、内存管理、设备驱动、文件系统管理、网络通信。
    • 权限:直接访问硬件,执行特权指令。
  2. 用户空间
    • 功能:运行应用程序(如GUI、Shell、服务进程)。
    • 权限:通过系统调用请求内核服务,无法直接操作硬件。

关键设计哲学:内核与用户空间的隔离确保了系统的稳定性。即使应用程序崩溃,内核仍可保持运行。


2.2 Bootloader

2.2.1 Bootloader启动流程

Bootloader是系统启动的第一阶段程序,负责初始化硬件并加载操作系统。其流程分为四步:

  1. CPU上电:执行ROM中的初始代码(如BIOS/UEFI),完成基础硬件初始化。
  2. Bootloader第一阶段:初始化内存控制器,为加载内核做准备。
  3. Bootloader第二阶段:从存储介质(如Flash、SD卡)加载内核和文件系统到内存。
  4. 内核执行:跳转到内核入口地址,移交系统控制权。

在这里插入图片描述

图2-2:Linux系统加载流程

2.2.2 常用Bootloader对比
Bootloader支持的架构特点Yocto支持
U-BootARM、MIPS、x86等嵌入式首选,高度可定制支持
GRUBx86、UEFI多系统引导,桌面/服务器适用支持
bareboxARM、MIPS轻量化设计,类似U-Boot支持
2.2.3 U-Boot:嵌入式系统的引导核心
  • 核心特性
    • 多架构支持(ARM、RISC-V等)。
    • 网络引导(TFTP、NFS),便于远程调试。
    • 命令行接口(CLI),支持动态配置启动参数。
  • 应用场景
    • 嵌入式设备启动Linux内核或Android系统。
    • 通过U-Boot脚本实现自动化测试。
# U-Boot命令行示例:设置内核启动参数
setenv bootargs console=ttyS0,115200 root=/dev/mmcblk0p2
bootm 0x82000000
2.2.4 GRUB:通用系统的引导标准
  • 核心特性
    • 支持多操作系统引导(Linux、Windows、macOS)。
    • 模块化设计,动态加载文件系统驱动。
    • 配置文件(grub.cfg)支持条件逻辑和主题定制。
  • 优势
    • 兼容UEFI固件,适用于现代服务器和PC。
    • 支持加密分区和LVM存储管理。

2.3 内核空间

2.3.1 Linux内核:系统的核心引擎
  • 核心功能

    • 硬件抽象:通过设备驱动管理CPU、内存、外设。
    • 资源调度:进程调度器(如CFS)公平分配CPU时间片。
    • 安全隔离:通过虚拟内存机制防止进程越权访问。
  • 内核版本管理

    版本类型特点适用场景
    稳定版(Stable)经过全面测试,修复已知漏洞生产环境
    长期支持版(LTS)提供2-6年维护企业级嵌入式系统
    主线版(Mainline)包含最新功能,未充分测试开发者验证新特性
2.3.2 控制硬件资源:内核的四大支柱
  1. 设备驱动
    • 功能:将硬件操作抽象为统一接口(如read()/write())。
    • 示例:网卡驱动处理数据包收发,GPU驱动渲染图形界面。
  2. 中断处理
    • 机制:硬件中断触发上下文切换,优先处理高优先级任务。
    • 应用:实时系统(如工业机器人)依赖低延迟中断响应。
  3. I/O管理
    • 优化:I/O调度算法(如CFQ、Deadline)减少磁盘寻道时间。
    • 技术:DMA(直接内存访问)释放CPU负载,提升吞吐量。
  4. 内存管理
    • 虚拟内存:通过MMU实现物理地址到虚拟地址的映射。
    • 内存保护:用户进程无法直接访问内核空间内存。
2.3.3 服务用户空间:内核的桥梁作用
  • 系统调用接口

    • 功能:提供300+系统调用(如open()fork())。
    • 示例:mmap()实现内存映射文件,提升I/O效率。
  • 进程管理

    • 调度策略:CFS(完全公平调度器)确保多任务公平性。
    • 实时扩展:RT-Preempt补丁支持微秒级任务响应。
  • 文件系统

    • 抽象层:VFS(虚拟文件系统)统一EXT4、XFS等接口。
    • 特性:日志功能(Journaling)防止数据丢失。
  • 网络子系统

    • 协议栈:TCP/IP实现可靠数据传输,QoS保障关键流量。
    • 安全机制:Netfilter框架支持防火墙和NAT功能。

    在这里插入图片描述

图2-3:用户空间与内核空间交互


2.4 用户空间

2.4.1 根文件系统:系统启动的基石
  • 目录结构:遵循FHS标准,关键目录包括:

    目录功能
    /bin基础命令(如lscp
    /etc配置文件(如网络设置、服务启动项)
    /lib共享库(如libc.so
    /dev设备节点(如/dev/sda1
  • 定制化:嵌入式系统常使用BusyBox替换GNU工具链,减少存储占用。

2.4.2 标准C库:开发者与内核的纽带
  • 核心作用
    • 封装系统调用,提供fopen()printf()等高级接口。
    • 优化性能(如缓冲区管理减少上下文切换开销)。
  • 实现对比
    库名称特点适用场景
    glibc功能全面,兼容性强通用Linux系统
    musl轻量化,静态链接优势嵌入式/容器环境
2.4.3 系统共享库:代码复用的艺术
  • 动态链接
    • 优点:减少内存占用,支持热更新。
    • 示例:libc.so被多个进程共享,无需重复加载。
  • 关键库
    • libm:数学运算(如三角函数、矩阵计算)。
    • libpam:可插拔认证模块(支持LDAP、指纹识别)。
2.4.4 init进程:用户空间的起点
  • 核心功能
    • 启动系统服务(如网络管理、日志守护进程)。
    • 管理进程生命周期(如孤儿进程回收)。
  • 实现方案
    init系统特点
    SysVinit简单可靠,脚本按顺序执行
    systemd并行启动,依赖关系自动解析
# systemd服务管理示例
systemctl start nginx.service
systemctl enable docker.service
2.4.5 窗口管理系统:图形界面的引擎
  • X11协议
    • 架构:客户端-服务器模型,支持远程显示。
    • 缺点:协议冗余,合成效率低。
  • Wayland
    • 优势:直接合成窗口,减少中间层开销。
    • 应用:Fedora、Ubuntu已默认支持Wayland。

在这里插入图片描述

图2-5:窗口管理系统架构


总结

Linux系统通过内核空间用户空间的协作,实现了硬件资源的高效管理和用户程序的稳定运行。从Bootloader的硬件初始化,到内核的进程调度,再到用户空间的应用程序,每一层都扮演着不可替代的角色。理解这些组件的设计原理和交互机制,是定制嵌入式Linux系统的关键基础。后续章节将结合Yocto项目,深入探讨如何优化和裁剪这些组件以满足特定需求,例如:

  • 如何为ARM设备编译最小化内核?
  • 如何通过Yocto定制根文件系统?
  • 如何选择适合的init系统和C库?

通过掌握这些知识,开发者能够构建出高性能、高可靠性的嵌入式Linux解决方案。


相关文章:

深入解析嵌入式Linux系统架构:从Bootloader到用户空间

B站视频链接,请多多关注本人B站: 📌 Yocto项目实战教程:第二章 视频讲解 目录 第2章 Linux系统架构 2.1 GNU/Linux2.2 Bootloader2.3 内核空间2.4 用户空间 总结 第2章 Linux系统架构 {#linux系统架构} 嵌入式Linux系统是Linux内核的精简版…...

一句话,十分钟,一部片!

大家好!我是羊仔,专注AI工具、智能体、编程。 羊仔最近发现一个超有意思的AI工具,简直是为内容创作者量身打造的!啥工具?Story-Flicks! 这玩意儿能干啥呢?简单来说,一句话&#xf…...

【橘子大模型】使用streamlit来构建自己的聊天机器人(下)

一、简介 我们之前完成了一个简易的聊天机器人,但是还留下了一些问题没有解决,比如如何开启新的会话。如何切换session_id,如何把对话做成流式的输出。这些我们就会在今天来完成。 二、关于新的会话和session_id from dotenv import load_…...

【合新通信】光纤延迟线(ODL)的原理

光纤延迟线是一种利用光学原理实现信号传输的设备,主要用于雷达、通信和测量等领域。以下是光纤延迟线的基本原理和工作方式: 技术原理 光纤延迟线通过相位控制器和分束器来处理输入信号。具体来说,数据信号和参考信号同时输入分束器&#x…...

Altium Designer——规则设置

规则 间距规则: 线宽:6mil > x > 4mil 1.在菜单栏中选择 设计 ——》 规则 根据下图双击对应的Clearance规则,更改红圈中的数字为6mil,然后点击应用再点击确定。 这个间距是元素之间(走线、铺铜、元器件&#x…...

智谛达科技:以创新为翼,翱翔AI人形机器人蓝海

在科技创新的浩瀚星空中,智谛达科技集团犹如一颗璀璨的明星,以其独特的创新光芒,照亮了AI人形机器人的广阔蓝海。这家在AI领域深耕多年的企业,始终秉持着创新为翼的发展理念,不断突破技术瓶颈,拓展应用场景,以卓越的实力和前瞻性的思维,引领着人形机器人行业的未来发展。 智谛达…...

前后端接口参数详解与 Mock 配置指南【大模型总结】

前后端接口参数详解与 Mock 配置指南 一、前端请求参数类型及 Mock 处理 1.1 URL 路径参数 (Path Parameters) 场景示例: GET /api/users/{userId}/orders/{orderId}Mock.js 处理: Mock.mock(/\/api\/users\/(\d)\/orders\/(\d)/, get, (options) &g…...

RPC与其他通信技术的区别,以及RPC的底层原理

1、什么是 RPC? 远程过程调用(RPC) 是一种协议,它允许程序在不同计算机之间进行通信,让开发者可以像调用本地函数一样发起远程请求。 通过 RPC,开发者无需关注底层网络细节,能够更专注于业务逻…...

汽车售后ODX 和 OTX 详细分析

在汽车售后诊断领域,ODX 和 OTX 都是重要的标准,但它们的应用场景和特点有所不同,难以简单地评判哪个是绝对的主流。以下是对它们的详细分析。 ODX(Open Diagnostic data eXchange) 概述:ODX 是由 ASAM 制…...

深度学习天崩开局

李沐大神的d2l包导入, 这玩意需要python311版本,我现在版本已经313了,作为一个天生要强的男人,我是坚决不向低版本低头的。 然后我就研究啊,各种翻资料啊,然后deepseek加豆包都翻烂了, 最终所…...

面试算法高频04-分治与回溯

分治与回溯 分治和回溯算法,包括其概念、特性、代码模板,并结合具体题目进行讲解,旨在帮助学员理解和掌握这两种算法的应用。 分治与回溯的概念 分治(Divide & Conquer):本质上基于递归,先…...

整数编码 - 华为OD统一考试(A卷、C++)

题目描述 实现一种整数编码方法,使得待编码的数字越小,编码后所占用的字节数越小。 编码规则如下: 编码时7位一组,每个字节的低7位用于存储待编码数字的补码。字节的最高位表示后续是否还有字节,置1表示后面还有更多的字节&…...

对访问者模式的理解

对访问者模式的理解 一、场景二、不采用访问者模式1、代码2、特点 三、采用访问者模式1、代码2、特点 四、思考 一、场景 我们有一个图形系统,系统中有多种图形对象(如圆形、方形等),每种图形对象都有不同的属性和行为。现在需要对…...

第三次PID状态机

以下是 apply_params 函数的实现步骤和代码示例: 1. 定义参数结构体 在头文件中定义 PID_Params 结构体,包含需要动态调整的 PID 参数: // ms_hal_photo_sensor.h typedef struct {float Kp; // 比例系数float Ki; // …...

如何在大型项目中有效使用TypeScript进行类型定义?

嗨,大家好,我是莫循,Typescript是JavaScript的超集,现在已经广泛用于前端开发,那么在项目中如何用好类型定义呢?以下是一些可以提供参考的案例实践。 一、类型组织策略 1. 模块化类型定义 按功能/模块划分…...

C4D XP 粒子动画云端渲染指南

在 C4D 动画制作领域,XP 粒子特效因其复杂的动力学计算常成为渲染瓶颈。传统本地渲染不仅耗时漫长,还需持续占用高配置硬件。而借助专业云渲染平台,创作者可突破物理限制,高效完成 XP 粒子动画的最终输出。 以渲染 101 平台为例&a…...

mysql知识总结 基础篇

Mysql知识总结 1. 执行一条sql语句 期间发生了什么?1. 如何查看mysql服务被多少个客户端链接了2. 空闲链接会一直闲置嘛?3. mysql的链接数量有限制嘛?4. 我们如何知道mysql要使用哪个索引5. 什么是覆盖索引 2. MySQL 一行记录是怎么存储的&am…...

基于条码数据生成校验密码的C++实现方案

前言 在医疗试剂、工业产品等需要严格追踪管理的领域,条码系统常被用于标识产品信息。本文将详细介绍4种用C实现的条码密码生成算法,这些算法可以根据条码前11位数据生成2位校验密码(第9、10位),用于数据校验或简单防…...

前端工具方法整理

文章目录 1.在数组中找到匹配项,然后创建新对象2.对象转JSON字符串3.JSON字符串转JSON对象4.有个响应式对象,然后想清空所有属性5.判断参数不为空6.格式化字符串7.解析数组内容用逗号拼接 1.在数组中找到匹配项,然后创建新对象 const modifi…...

[数据结构]图krusakl算法实现

目录 Kruskal算法 Kruskal算法 我们要在连通图中去找生成树 连通图:在无向图中,若从顶点v1到顶点v2有路径,则称顶点v1与顶点v2是连通的。如果图中任意一对顶点都是连通的,则称此图为连通图。 生成树:一个连通图的最小…...

18-产品经理-跟踪进度

禅道是一个可以帮助产品经理跟踪研发进度的系统。通过禅道,产品经理可以从多个角度了解产品的研发状态。在仪表盘中,可以展示所有产品或单一产品的概况,包括需求、计划和发布数量,研发需求状态,Bug修复率和计划发布数。…...

华为机试—挑7

题目 你需要统计 1 到 n 之间与 7 有关的数字的个数。 与 7 有关的数字包括: 是 7 的倍数(如 7,14,21 等);包含数字 7(如 17,27,37,⋯ ,70,71,72,⋯等)。 示例 输入:20 输出:3 说…...

【区块链安全 | 第三十四篇】合约审计之重入漏洞

文章目录 概念漏洞代码代码审计攻击代码攻击过程总结示例修复建议审计思路 概念 以太坊的智能合约可以互相调用,也就是说,一个合约可以调用另一个合约的函数。除了外部账户,合约本身也可以持有以太币并进行转账。当合约接收到以太币时&#…...

Java虚拟机——JVM(Java Virtual Machine)解析一

1.JVM是什么? 1.1 JVM概念 Java Virtual Machine (JVM) 是JDK的核心组件之一,它使得 Java 程序能够在任何支持 JVM 的设备或操作系统上运行,而无需修改源代码 JDK是什么,JDK和JVM是什么关系?1.Java IDE(Integrated …...

【JVM】question

问题 JVM线程是用户态还是内核态 java线程在jdk1.2之前,是基于名为“绿色线程”的用户线程实现的,这导致绿色线程只能同主线程共享CPU分片,从而无法利用多核CPU的优势。 由于绿色线程和原生线程比起来在使用时有一些限制, jdk1.2…...

页面编辑器CodeMirror初始化不显示行号或文本内容

延迟刷新 本来想延迟100毫秒的,但是会出现样式向左偏移的情况,于是试了试500毫秒,发现就没有问题了,可能是样式什么是需要一个加载过程吧。 useEffect(() > {editorRef.current?.setValue(value || );setTimeout(() > {edi…...

顺序表——C语言实现

目录 一、线性表 二、顺序表 1.实现动态顺序表 SeqList.h SeqList.c Test.c 问题 经验:free 出问题,2种可能性 解决问题 (2)尾删 (3)头插,头删 (4)在 pos 位…...

OpenCV 图形API(21)逐像素操作

操作系统:ubuntu22.04 OpenCV版本:OpenCV4.9 IDE:Visual Studio Code 编程语言:C11 算法描述 在OpenCV的G-API模块中,逐像素操作指的是对图像中的每个像素单独进行处理的操作。这些操作可以通过G-API的计算图(Graph …...

车载联网终端4G汽车TBOX介绍定义与概述

汽车 TBOX(Telematics Box)是专为汽车设计的远程通信终端设备,属于车联网系统的关键组成部分。车联网系统一般包含主机、汽车 T - BOX、手机 APP 及后台系统。融合了车身网络和 4G 无线通信技术,为汽车提供丰富的 Telematics 服务…...

CentOS无法安装Vim文本编辑器问题以及解决方法

1.问题一:用户权限不够 解决方法一:切换到root用户 解决方法二:给本用户添加权限 2.问题二:镜像源问题:官方镜像源可能已经失效 解决方法: 1. 检查网络连接 2. 检查和配置 DNS 3. 更换镜像源&#…...

Kettle如何与应用集成

Kettle(Pentaho Data Integration,PDI)可以通过多种方式与应用程序集成,以下是7种主流方法及具体实现示例: 一、命令行调用(最基础) # 执行转换(Transformation) ./pan.…...

Pytorch torch.nn.utils.rnn.pad_sequence 介绍

torch.nn.utils.rnn.pad_sequence 是 PyTorch 中一个用于填充序列的实用函数,它主要用于处理长度不一的序列数据,将这些序列填充到相同的长度,以便能将它们组合成一个批量(batch)输入到神经网络中。以下是详细介绍&…...

4.7正则表达式

1.字符匹配 一般字符匹配自身. 匹配任意字符(换行符\n除外),一个点占一位\转义字符,使其后一个字符改变原来的意思(\.就是.)[......]字符集,对应的位置可以是字符集中的任意字符.字符集中的字符可以逐个列出,也可以给出范围如[abc]或[a-c] [^abc] 表示取反&#xf…...

CogPatInspectTool工具

CogPatInspectTool是康耐视中的一种模板比对的视觉检测工具,主要用于产品不良检测。其核心功能是通过将输入图像与预先训练好的模板进行对比,识别出两者之间的差异,并生成高亮差异图,从而判断产品是否存在缺陷。 效果图 CogPatIn…...

牛客周赛 + 洛谷刷题

秘藏 #include<bits/stdc.h> using namespace std; typedef long long ll; const int N 200010; ll a[N], b[N]; int n, k; ll dp[2][N];//dp[i][j]是在i界中取了j之前的最大值 int main(){ios::sync_with_stdio(false), cin.tie(0), cout.tie(0);cin >> n >&…...

【数据结构】图论存储革新:十字链表双链设计高效解决有向图入度查询难题

十字链表 导读一、邻接表的优缺点二、十字链表2.1 结点结构2.2 原理解释2.2.1 顶点表2.2.2 边结点2.2.3 十字链表 三、存储结构四、算法评价4.1 时间复杂度4.2 空间复杂度 五、优势与劣势5.1 优势5.2 劣势5.3 特点 结语 导读 大家好&#xff0c;很高兴又和大家见面啦&#xff…...

【JavaScript】十五、事件对象与环境对象

文章目录 1、事件对象1.1 获取事件对象1.2 常用属性1.3 案例&#xff1a;回车发布评论 2、环境对象this3、回调函数4、案例&#xff1a;tab切换5、案例&#xff1a;全选文本框&#x1f4d6; 1、事件对象 事件对象&#xff1a; 也是个对象&#xff0c;object&#xff0c;里面存…...

OJ--第N个泰波那契数列

1137. 第 N 个泰波那契数 - 力扣&#xff08;LeetCode&#xff09; 1 题干部分 2 拆解 1 状态表示&#xff1a;dp[i] 2 状态转移方程:dp[i]dp[i-1]dp[i-2]dp[i-3] 3 初始化:让dp[0]0,dp[1]dp[2]1 4 填表顺序:从dp[3]开始填从左往右填 5 返回值&#xff1a;dp[n]即为返回的…...

Python从入门到高手8.1节-元组类型详解

目录 8.1.1 理解元组类型 8.1.2 元组的类型名 8.1.3 元组的定义 8.1.4 元组的解包 8.1.5 元组是可迭代的 8.1.6 假期就这么结束了 8.1.1 理解元组类型 元组与列表有着相同的数据结构&#xff0c;区别在于&#xff0c;元组是不可变的数据类型&#xff0c;而列表是可变的数…...

使用 Qt 和 OBS 工具检测系统硬件编码器支持情况(NVENC、QSV、AMF)

在开发涉及视频处理的软件时,判断系统是否支持硬件加速编码器(如 NVIDIA NVENC、Intel QSV、AMD AMF)对于性能优化至关重要。本文将介绍如何结合 Qt 与 OBS Studio 附带的小工具程序,实现一个完整、异步且不会卡住 UI 的硬件加速检测模块。 一、背景与目标 硬件加速编码器…...

Python爬虫生成CSV文件的完整流程

引言 在当今数据驱动的时代&#xff0c;网络爬虫已成为获取互联网数据的重要工具。Python凭借其丰富的库生态系统和简洁的语法&#xff0c;成为了爬虫开发的首选语言。本文将详细介绍使用Python爬虫从网页抓取数据并生成CSV文件的完整流程&#xff0c;包括环境准备、网页请求、…...

图论:多源最短路

多源最短路 B3647 【模板】Floyd - 洛谷 #include<iostream> #include<cstring> using namespace std;const int N 110; int f[N][N]; int n, m;int main() {memset(f, 0x3f, sizeof(f));//对于重边的处理取较小值&#xff0c;所以要把全部都初始化成无穷大&…...

2024年已备案大模型发展趋势分析

2024年已备案大模型发展趋势分析 随着生成式人工智能技术的快速发展,其在各个领域的应用逐渐深入。为了规范和促进生成式人工智能服务的健康发展,国家互联网信息办公室发布了《生成式人工智能服务已备案信息》。本文将基于已备案信息,分析生成式人工智能服务的发展趋势,并…...

spring功能汇总

1.创建一个dao接口&#xff0c;实现类&#xff1b;service接口&#xff0c;实现类并且service里用new创建对象方式调用dao的方法 2.使用spring分别获取dao和service对象(IOC) 注意 2中的service里面获取dao的对象方式不用new的(DI) 运行测试&#xff1a; 使用1的方式创建servic…...

Transformer - Feed Forward前馈网络

一、数学原理 1. 前馈神经网络公式 2. Dropout公式 二、代码实现 import math import torchimport torch.nn as nnclass FeedForward(nn.Module):def __init__(self, d_model, dff, dropout):super().__init__()self.W1 nn.Linear(d_model, dff)self.W2 nn.Linear(dff, d_mo…...

Compose Multiplatform+Kotlin Multiplatfrom 第五弹跨平台 截图

截图功能 Compose MultiplatformKotlin Multiplatfrom下实现桌面端的截图功能&#xff0c;起码搞了两星期&#xff0c;最后终于做出来了&#xff0c;操作都很流畅&#xff0c;截取的文件大小也正常&#xff0c;可参考支持讨论&#xff01; 功能效果 代码实现 //在jvmMain下创…...

算法题(119):高精度减法

审题&#xff1a; 本题高精度减法主要是要区分正负号&#xff0c;然后进行模拟 思路&#xff1a; 方法一&#xff1a;模拟法 首先本题需要我们利用字符串进行大数相减 第一步&#xff1a;区分s1和s2谁更大 先从数的位数进行判断&#xff0c;然后再从高到低的位数进行判断 第二步…...

使用成员函数指针数组简化C++类中的操作

使用成员函数指针数组简化C类中的操作 在C编程中&#xff0c;我们常常会遇到需要对一组相似的操作进行处理的情况。例如&#xff0c;在一个游戏引擎中&#xff0c;你可能希望角色能够执行一系列的动作&#xff0c;如行走、跳跃或攻击等。为了简化这些操作的管理和调用&#xf…...

WebGL数学手记:矩阵基础

一、矩阵的定义 矩阵&#xff0c;数学术语。在数学中&#xff0c;矩阵&#xff08;Matrix&#xff09;是一个按照长方阵列排列的复数或实数集合。 1.英文发音&#xff08;Matrix&#xff09; Matrix的发音类似于中文的[美吹克斯]&#xff0c;知道它的发音。方便后期看教程时…...

Python爬取数据(二)

一.example2包下的 1.re模块的compile函数使用 import repatternre.compile(r\d) print(pattern) 2.match的方法使用 import re patternre.compile(r\d) # m1pattern.match(one123twothree345four) #参数2&#xff1a;指定起始位置(包含),参数3&#xff1a;终止位置(包含),…...