Linux内核学习轨迹第五部:反向映射RMAP机制全解析(第八小节)

Linux Swap 子系统:架构、内存管理与虚拟化 Swap Linux Swap机制通过将不活跃内存页移至磁盘或压缩内存,扩展系统有效内存容量,缓解内存压力。传统架构中,逻辑Swap槽与物理存储绑定,导致资源浪费,尤其在使用Zswap等压缩技术时。为此,Vswap与Xswap提出虚拟化方案:前者以XArray实现灵活映射,支持多后端迁移;后者采用稀疏映射,简化管理但容量固定。二者在架构设计、资源记账与动态扩展上各有权衡,反映了内核开发中对性能、可维护性与灵活性的深层考量。 阅读详情

8. 反向映射RMAP机制全解析

反向映射(Reverse Mapping, RMAP)是Linux内存管理中最核心、也最容易被忽略的机制,它解决了一个核心问题:给定一个物理页,如何快速找到所有映射了这个页的进程页表项。
没有反向映射之前,内核要回收一个物理页,必须遍历系统中所有进程的所有页表,查找是否有映射了这个页的页表项,时间复杂度极高,完全不可用。反向映射机制的出现,让内核可以在O(1)~O(n)的时间复杂度内,找到所有映射了该页的页表项,是内存回收、页迁移、COW写时复制、KSM同页合并等机制的底层基础。
本章节基于Linux 6.6 LTS内核,完整拆解反向映射的设计思想、核心数据结构、匿名页与文件页的反向映射实现、全链路操作流程。

8.1 反向映射的核心设计目标

  1. 快速查找页表项:给定一个物理页,能快速找到所有映射了这个页的进程页表项,用于修改页表项(比如回收页时清除页表项、页迁移时修改页表项的物理地址);
  2. 最小化内存开销:反向映射的元数据开销必须极小,不能占用大量内存,尤其是系统中有海量进程、海量物理页的场景;
  3. 高性能的操作接口:反向映射的遍历、添加、删除操作必须高效,不能成为内存管理的性能瓶颈;
  4. 支持复杂场景:支持私有映射、共享映射、写时复制、线程共享地址空间、大页等复杂场景。

8.2 反向映射的核心分类

Linux的反向映射分为两大类,分别对应两种不同类型的页:
  1. 文件页的反向映射:基于struct address_space和优先级搜索树(Interval Tree)实现,用于页缓存中的文件页,包括可执行文件、共享库、数据文件的映射页;
  2. 匿名页的反向映射:基于struct anon_vma和anon_vma_chain实现,用于没有后备文件的匿名页,包括堆、栈、mmap匿名映射的页。
两者的核心差异:文件页的后备存储是磁盘文件,所有映射了该文件同一偏移的进程,共享同一个页缓存,反向映射的核心是找到所有映射了该文件偏移的VMA;匿名页没有后备文件,是进程私有的(COW之前),反向映射的核心是找到所有共享该页的VMA。

8.3 文件页的反向映射实现

文件页的反向映射是Linux最早实现的反向映射机制,设计相对简单,基于文件的地址空间和VMA的区间树实现。

8.3.1 核心数据结构

struct address_space:每个打开的文件对应一个address_space实例,管理该文件的页缓存,是文件页反向映射的核心锚点,定义在include/linux/fs.h中,核心字段:

struct address_space {
    // 文件的宿主inode
    struct inode *host;
    // 页缓存的XArray,存储该文件的所有缓存页
    struct xarray i_pages;
    // 映射了该文件的所有VMA的区间树,反向映射的核心
    struct maple_tree i_mmap;
    // 地址空间的自旋锁
    rwlock_t i_mmap_rwsem;
    // 脏页、回写相关字段
    unsigned long nrpages;
    struct writeback_control *writeback;
};

核心字段i_mmap:Maple Tree(枫树树,Linux 6.2+替换了之前的优先级搜索树),存储所有映射了该文件的VMA,每个VMA对应文件的一个偏移区间,通过文件偏移可以快速找到所有映射了该偏移的VMA。

struct vm_area_struct:每个文件映射的VMA,会被插入到对应文件的address_space->i_mmap区间树中,key是VMA映射的文件偏移区间[vm_pgoff, vm_pgoff + (vm_end - vm_start)/PAGE_SIZE]。

8.3.2 文件页反向映射的核心流程

文件页反向映射的核心目标是:给定一个文件页(对应文件的inode和页内偏移),找到所有映射了该页的VMA,然后通过VMA和虚拟地址,找到对应的页表项。
完整执行流程:
  1. 从物理页的struct page结构体中,获取对应的address_space(page->mapping)和页内偏移page->index;
  2. 加i_mmap_rwsem读锁,遍历address_space->i_mmap区间树,找到所有映射了该文件偏移page->index的VMA;
  3. 对于每个找到的VMA,计算该页在VMA中的虚拟地址:vma->vm_start + (page->index - vma->vm_pgoff) * PAGE_SIZE;
  4. 通过VMA所属的mm_struct(vma->vm_mm)和虚拟地址,遍历页表,找到对应的页表项;
  5. 对页表项执行对应的操作:比如内存回收时清除页表项、页迁移时修改页表项的物理地址、设置页表项为只读(COW)等。
核心工程细节:
  1. 文件页的反向映射,只需要存储文件的address_space和页内偏移,不需要为每个页存储额外的元数据,内存开销极小;
  2. Maple Tree的区间查询效率极高,O(logn)时间复杂度就能找到所有映射了该偏移的VMA;
  3. 同一个文件的多个共享映射、私有映射,都会被插入到同一个i_mmap区间树中,一次遍历就能找到所有映射了该页的VMA。

8.4 匿名页的反向映射实现

匿名页没有后备文件,无法像文件页那样基于address_space做反向映射,而且匿名页会通过fork()被多个进程共享(COW),反向映射的设计比文件页复杂得多。Linux采用了基于anon_vma和anon_vma_chain的匿名页反向映射机制,完美解决了COW场景下的反向映射问题。

8.4.1 核心设计思想

匿名页反向映射的核心设计是:每个匿名VMA对应一个anon_vma结构体,所有共享该匿名页的VMA,都会被链接到同一个anon_vma中,通过anon_vma可以找到所有映射了该匿名页的VMA。
fork()创建子进程时,子进程会复制父进程的匿名VMA,同时创建anon_vma_chain,把子进程的VMA链接到父进程的anon_vma中,这样,父进程的匿名页被共享后,通过anon_vma就能找到所有子进程中映射了该页的VMA。

8.4.2 核心数据结构

struct anon_vma:匿名页反向映射的核心锚点,管理所有映射了同一组匿名页的VMA,定义在include/linux/rmap.h中:

struct anon_vma {
    // 保护该结构的自旋锁
    struct rw_semaphore rwsem;
    // 所有链接到该anon_vma的VMA的链表
    struct rb_root rb_root;
    // 该anon_vma对应的根VMA
    struct vm_area_struct *root_vma;
    // 引用计数
    atomic_t refcount;
};

核心字段rb_root:红黑树,存储所有链接到该anon_vma的VMA,通过虚拟地址可以快速找到对应的VMA。

struct anon_vma_chain:连接VMA和anon_vma的桥梁,每个VMA和anon_vma的对应关系,都有一个anon_vma_chain实例,定义在include/linux/rmap.h中:

struct anon_vma_chain {
    // 对应的VMA
    struct vm_area_struct *vma;
    // 对应的anon_vma
    struct anon_vma *anon_vma;
    // 加入anon_vma->rb_root的红黑树节点
    struct rb_node rb;
    // 加入VMA的anon_vma_chain链表的节点
    struct list_head same_vma;
};

每个VMA有一个anon_vma_chain链表,链接了所有和该VMA关联的anon_vma;

每个anon_vma有一个红黑树,链接了所有和该anon_vma关联的VMA。

struct page中的反向映射字段:匿名页的page->mapping字段,设置为PAGE_MAPPING_ANON,表示这是匿名页,page->anon_vma指向该页对应的anon_vma,page->index是该页在VMA中的虚拟地址偏移。

8.4.3 匿名页反向映射的核心流程

匿名页反向映射的核心目标是:给定一个匿名页,找到所有映射了该页的VMA,然后找到对应的页表项。
完整执行流程:
  1. 从物理页的struct page结构体中,确认是匿名页(PAGE_MAPPING_ANON),获取对应的anon_vma(page_anon_vma(page))和页的虚拟地址偏移page->index;
  2. 加anon_vma->rwsem读锁,遍历anon_vma->rb_root红黑树,找到所有包含该偏移的VMA;
  3. 对于每个找到的VMA,计算该页在VMA中的虚拟地址:vma->vm_start + (page->index - vma->vm_pgoff) * PAGE_SIZE;
  4. 通过VMA所属的mm_struct和虚拟地址,遍历页表,找到对应的页表项;
  5. 对页表项执行对应的操作:清除页表项、修改物理地址、设置只读等。

8.4.4 fork()场景下的反向映射处理

fork()创建子进程时,会复制父进程的所有VMA,包括匿名VMA,同时处理匿名反向映射:
  1. 子进程复制父进程的匿名VMA,创建新的VMA结构体;
  2. 为子进程的VMA创建新的anon_vma_chain实例;
  3. 把子进程的VMA,通过anon_vma_chain链接到父进程的anon_vma中;
  4. 同时,为子进程的VMA创建新的anon_vma,用于子进程后续新建的匿名页;
  5. 父子进程的匿名页的页表项都设置为只读,后续写入时触发COW异常。
这样,父进程的匿名页对应的anon_vma,就链接了父子进程的所有VMA,通过反向映射就能找到所有映射了该页的VMA,完美支持COW场景。

8.5 反向映射的核心应用场景

反向映射是Linux内存管理的基础设施,几乎所有的内存操作都依赖反向映射,核心应用场景:
  1. 内存回收:内核回收一个物理页时,必须通过反向映射找到所有映射了该页的页表项,清除页表项,刷新TLB,然后才能释放物理页。如果没有反向映射,内存回收完全无法实现;
  2. 写时复制COW:COW异常处理时,需要通过反向映射找到所有共享该页的页表项,修改页表项,确保只有触发异常的进程复制新页,其他进程的页表项保持不变;
  3. 页迁移:内存碎片整理、内存热插拔、NUMA平衡时,需要把物理页从一个地址迁移到另一个地址,必须通过反向映射找到所有映射了该页的页表项,修改页表项的物理地址,刷新TLB,保证进程访问不受影响;
  4. KSM同页合并:内核同页合并机制(KSM),会把内容相同的匿名页合并为一个只读页,减少内存占用,必须通过反向映射找到所有映射了原页的页表项,修改为指向合并后的页;
  5. 页错误处理:处理页被换出swap、页被锁定等异常时,需要通过反向映射找到对应的页表项,修改页表项的状态。

8.6 工程实践与认知纠正

1.反向映射的内存开销认知

很多工程师误以为反向映射会占用大量内存,实际上:
  1. 文件页的反向映射,元数据存储在文件的address_space中,每个文件只需要一个区间树,内存开销极小;
  2. 匿名页的反向映射,anon_vma和anon_vma_chain的数量和VMA的数量成正比,而不是和物理页的数量成正比,哪怕系统中有几十GB的内存,反向映射的元数据开销也只有几MB,完全可以忽略;
  3. 内核做了大量的优化,比如anon_vma的复用、红黑树的高效管理,最小化内存开销。

2.反向映射的性能优化

反向映射的遍历是内存回收、页迁移的核心开销,内核做了大量的性能优化:
  1. 用Maple Tree替换了传统的优先级搜索树,区间查询的性能提升了30%以上;
  2. 反向映射的遍历采用RCU机制,读操作不需要加排他锁,允许多个CPU并发遍历;
  3. 内存回收时,优先回收只有一个映射的页(_mapcount == 0),不需要遍历反向映射,提升回收效率;
  4. 页迁移时,优先迁移映射数量少的页,减少反向映射的遍历开销。

3.反向映射的调试与排查

反向映射的异常会导致内核崩溃、内存泄漏、OOM等问题,内核提供了相应的调试手段:
  1. 开启CONFIG_DEBUG_RMAP内核配置,开启反向映射的调试检查,检测非法的VMA链接、引用计数泄漏等问题;
  2. 用/proc/pid/maps查看进程的VMA,确认匿名VMA的anon_vma是否正常;
  3. 用crash工具分析内核coredump,查看anon_vma的红黑树、VMA的链表,定位反向映射的异常。

4.认知纠正:匿名页的共享范围

很多工程师误以为匿名页是进程私有的,实际上,通过fork(),匿名页会被父子进程共享,直到触发COW,反向映射机制就是为了处理这种共享场景。如果没有反向映射,fork()之后的COW完全无法实现,这也是反向映射机制最核心的设计目标。
第八章 GPU 调度器:8.1 命令提交的演进 本文系统阐述了GPU命令提交的四大演进方向:地址确定、BO就位保障、作业同步机制与队列仲裁权转移。从早期内核主导的ioctl提交,逐步发展为用户态直接写入硬件队列,结合虚拟内存、缺页处理与固件调度,实现提交路径简化与性能提升。各方向相互关联,共同推动内核职责向绑定、驱逐、缺页及固件阶段转移,核心约束——内核对内存访问的最终控制力——始终不变。 阅读详情

相关推荐

国央企创新负责人如何通过平台实现科研成果的快速识别与转化?.docx

科易网基于AI模型+行业大数据,在技术转移、成果转化、技术经纪、知识产权、产业创新、科技招商等垂直领域的多样化应用场景,推出科技创新领域的AI+工具与数智化解决方案,推动科技创新与产业创新智能化发展。

内存管理-Autoreleasepool

Autoreleasepool目前通过@autoreleasepool{}来创建,可以再适当的时机对对象调用release,保证了对象的延迟释放AutoreleasePoolPage底层结构AutoreleasePoolPage是以栈为结点通过双向链表的形式组合而成;遵循先进后出规则,整个自动释放池由一系列的组成的,而是以双向链表的形式连接起来。自动释放池与线程一一对应;调用来入栈,调用来出栈使用哨兵对象来作为出入栈的标志位只是nil的别名。前世叫做POOL_SENTINEL,称为。

ymsjk的博客 345

在WPS/Office中免费使用AI,快速提升办公效率!​

《免费解锁WPS/Office AI办公神器教程》摘要: 本教程详解如何通过第三方插件OfficeAI免费实现WPS/Office智能办公,突破官方付费限制。从安全设置到安装配置,手把手教学,涵盖文档生成、PPT美化、Excel图表等核心功能。关键优势包括零成本、全场景支持及云端/本地双模式切换,并附常见问题解决方案。注意需使用WPS 2024+版本,安装时需临时关闭杀毒软件。教程强调工具来源合法性,建议商用购买正版授权。(149字)

杜哥无敌的博客 2303

【C++】内存管理

本文系统梳理程序内存布局:局部变量在栈,动态分配在堆,全局与静态变量在数据段,字符串字面量在代码段。对比malloc/free与new/delete,强调后者自动调用构造/析构函数,实现内存管理与对象生命周期的统一。详解new[]/delete[]如何记录数组大小并逆序析构,揭示内存泄漏成因——如指针混用、重复释放、未正确配对等,并提出预防策略。核心贯穿问题:空间由谁申请、谁释放、何时构造/析构。

记录在学习过程中学到的知识 337

【win11+vs 2017+OpenCV4.5.5+Qt5.12配置】详细安装过程+小问题解决

由于Qt5无法与最新的vs2022兼容,扩展工具中一直显示不可用,所以将vs降级成vs2017。在安装Qt的过程中,会选择安装Qt套件,其中就的MCVS 2017,说明vs2017是与qt兼容的。当然也可以用qt creator这一原生IDE。OpenCV版本目前是最新的4.8.0,使用过程中没有什么问题,但是还是安装低版本大概率避免一些玄学问题。

qq_45306739的博客 3350

unity C# 计算3D空间任意多边形面积,距离,角度测量工具

unity C# 计算3D空间任意多边形面积,距离,角度 using UnityEngine; using System.Collections; using System.Collections.Generic; using UnityEngine.UI; using System; /// /// 划线面积,距离,角度 /// public class UnderlinedMeasureTool : MonoBehaviour { /// /// 相机 /// public Camera _c

qq_22972867的博客 2224

用户态申请内存 vs 内核态申请内存:对系统内存管理的影响

用户态分配的内存与内核态分配的内存,在等方面有本质区别。厘清这一区别,是理解memfdudmabufuserptr、SVM/HMM、dma-buf、CMA、大页等一系列机制的。本文集中论述二者对系统内存管理的影响,并给出典型用例。

图形/计算GPU的驱动与虚拟化技术分享园地 175

Python高效转换病理图像:从mrxs到SVS的完整实践指南

本文提供了使用Python将数字病理切片从mrxs格式高效转换为SVS格式的完整实践指南。针对mrxs格式兼容性差的问题,文章详细解析了基于openslide和tifffile库的核心转换流程,并重点分享了应对大内存消耗的优化方案与流式处理技巧,确保转换后的SVS文件保留多分辨率金字塔结构,兼容主流病理分析工具。

weixin_29051811的博客 547

Java方法学习总结:方法区内存结构总结

本文总结了方法区是JVM规范定义的逻辑区域,用于存储类元数据、常量池等信息,而非固定物理分区。不同JVM实现可采用不同方式:HotSpot JDK 7及以前用永久代,JDK 8后改用元空间,但均满足规范要求。方法区逻辑上属于堆,但物理上可独立于堆内存,其具体实现由JVM自行决定,以适应不同的内存管理策略与操作系统特性。理解方法区的关键在于区分逻辑概念与物理实现。

wuminyu的博客 598

绿联UGOS Pro系统虚拟机部署Windows 11详细教程(跳账户登录,安装内存驱动)

总的来说,此次的虚拟机部署Windows 11出现的问题应该是目前几乎所有虚拟机都可能出现的问题,和绿联是没有关系的。所以说如果你在其它NAS上虚拟机部署Windows 11系统如果出现同样的问题,那么今天教程的方案也同样适用于你。

qq_63499861的博客 1万+

【系统架构设计师】预测试卷一:综合知识(75道选择题)

软件架构风格是描述某一特定应用领域中系统组织方式的惯用模式,架构风格反映领域中众多系统所共有的结构和 (48),强调对架构(49)的重用。 (48) A. 语义特性 B. 功能需求 C. 质量属性 D. 业务规则 (49) A. 分析 B. 设计 C.实现

数据知道的博客 7766

第20讲:处理器下内存管理的发展历程

处理器内存管理历经三阶段演进:实模式下,8086引入分段机制,通过“段基址+偏移量”实现20位寻址,支持程序动态重定位;保护模式中,80386启用GDT与段描述符,实现权限控制(DPL)、地址隔离与虚拟内存调度;最终因段机制导致碎片大、不适应4GB寻址需求,系统转向平坦模式,以页式管理为主。分页机制成为现代内存管理核心,实现高效、安全的虚拟内存管理。

2301_80791727的博客 296

基于Simulink的PID控制防抱死制动系统(ABS)建模与仿真

防抱死制动系统(Anti-lock Braking System,简称ABS)是一种用于防止车辆在紧急制动时车轮完全抱死的技术。通过实时监测车轮速度并调节制动力,ABS能够显著提高车辆的制动性能和操控稳定性,从而减少交通事故的发生。PID(比例-积分-微分)控制器因其结构简单、性能稳定且易于实现而被广泛应用于ABS控制系统中。本项目旨在通过MATLAB/Simulink平台设计和验证一个基于PID控制的ABS系统,重点研究PID参数调优方法、系统动态响应特性以及制动过程中的滑移率控制能力。

MHD0815的博客 484

《C++深度解构06》手撕 string —— 从底层内存管理到深浅拷贝彻底吃透

本文通过手写C++ string类,深入剖析动态内存管理、深浅拷贝、异常安全及容量控制等核心机制。基于命名空间封装,实现全缺省构造、析构与只读接口,结合reserve动态扩容策略(初始4字节,后续翻倍),确保内存安全与性能优化。重点强调nullptr防护、资源置换安全及静态成员初始化规范,揭示标准库底层逻辑,助力开发者掌握数据结构本质。

huhuiyuan_的博客 485

白皮精读:70页 2025 基于数据空间的金融数据可信流通研究报告【附全文阅读】

金融数据可信流通面临法规、技术与商业模式的挑战。报告分析国内外发展现状,提出基于数据空间的可信流通框架,包含典型场景、技术方案与流通模式。实践案例显示,隐私计算、区块链等技术可提升风控效率与合规性。建议完善数据分类分级、统一技术标准并推动行业试点,以释放数据要素价值,促进数字经济发展。

cdfunlove的博客 848

深度学习工具包 DeepLearningToolbox

深度学习工具包Deprecation notice.-----This toolbox is outdated and no longer maintained.There are much better tools available for deep learning than this toolbox, e.g. [Theano](http://deeplearning.net/software/theano/), [torch](http://torch.ch/) or [tensorflow](http://www.tensorflow.org/)I would suggest you use one of the tools mentioned above rather than use this toolbox.Best, Rasmus.DeepLearnToolbox================A Matlab toolbox for Deep Learning.Deep Learning is a new subfield of machine learning that focuses on learning deep hierarchical models of data.It is inspired by the human brain's apparent deep (layered, hierarchical) architecture.A good overview of the theory of Deep Learning theory is[Learning Deep Architectures for AI](http://www.iro.umontreal.ca/~bengioy/papers/ftml_book.pdf)For a more informal introduction, see the following videos by Geoffrey Hinton and Andrew Ng.* [The Next Generation of Neural Networks](http://www.youtube.com/watch?v=AyzOUbkUf3M) (Hinton, 2007)* [Recent Developments in Deep Learning](http://www.youtube.com/watch?v=VdIURAu1-aU) (Hinton, 2010)* [Unsupervised Feature Learning and Deep Learning](http://www.youtube.com/watch?v=ZmNOAtZIgIk) (Ng, 2011)If you use this toolbox in your research please cite [Prediction as a candidate for learning deep hierarchical models of data](http://www2.imm.dtu.dk/pubdb/views/publication_details.php?id=6284)```@MASTERSTHESIS\{IMM2012-06284, author = "R. B. Palm", title = "Prediction as a candidate for learning deep hierarchical models of data", year = "2012",}```Contact: rasmusbergpalm at gmail dot comDirectories included in the toolbox-----------------------------------`NN/` - A library for Feedforward Backpropagation Neural Networks`CNN/` - A library for Convolutional Neural Networks`DBN/` - A library for Deep Belief Networks`SAE/` - A library for Stacked Auto-Encoders`CAE/` - A library for Convolutional Auto-Encoders`util/` - Utility functions used by the libraries`data/` - Data used by the examples`tests/` - unit tests to verify toolbox is workingFor references on each library check REFS.mdSetup-----1. Download.2. addpath(genpath('DeepLearnToolbox'));Example: Deep Belief Network---------------------```matlabfunction test_example_DBNload mnist_uint8;train_x = double(train_x) / 255;test_x = double(test_x) / 255;train_y = double(train_y);test_y = double(test_y);%% ex1 train a 100 hidden unit RBM and visualize its weightsrand('state',0)dbn.sizes = [100];opts.numepochs = 1;opts.batchsize = 100;opts.momentum = 0;opts.alpha = 1;dbn = dbnsetup(dbn, train_x, opts);dbn = dbntrain(dbn, train_x, opts);figure; visualize(dbn.rbm{1}.W'); % Visualize the RBM weights%% ex2 train a 100-100 hidden unit DBN and use its weights to initialize a NNrand('state',0)%train dbndbn.sizes = [100 100];opts.numepochs = 1;opts.batchsize = 100;opts.momentum = 0;opts.alpha = 1;dbn = dbnsetup(dbn, train_x, opts);dbn = dbntrain(dbn, train_x, opts);%unfold dbn to nnnn = dbnunfoldtonn(dbn, 10);nn.activation_function = 'sigm';%train nnopts.numepochs = 1;opts.batchsize = 100;nn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.10, 'Too big error');```Example: Stacked Auto-Encoders---------------------```matlabfunction test_example_SAEload mnist_uint8;train_x = double(train_x)/255;test_x = double(test_x)/255;train_y = double(train_y);test_y = double(test_y);%% ex1 train a 100 hidden unit SDAE and use it to initialize a FFNN% Setup and train a stacked denoising autoencoder (SDAE)rand('state',0)sae = saesetup([784 100]);sae.ae{1}.activation_function = 'sigm';sae.ae{1}.learningRate = 1;sae.ae{1}.inputZeroMaskedFraction = 0.5;opts.numepochs = 1;opts.batchsize = 100;sae = saetrain(sae, train_x, opts);visualize(sae.ae{1}.W{1}(:,2:end)')% Use the SDAE to initialize a FFNNnn = nnsetup([784 100 10]);nn.activation_function = 'sigm';nn.learningRate = 1;nn.W{1} = sae.ae{1}.W{1};% Train the FFNNopts.numepochs = 1;opts.batchsize = 100;nn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.16, 'Too big error');```Example: Convolutional Neural Nets---------------------```matlabfunction test_example_CNNload mnist_uint8;train_x = double(reshape(train_x',28,28,60000))/255;test_x = double(reshape(test_x',28,28,10000))/255;train_y = double(train_y');test_y = double(test_y');%% ex1 Train a 6c-2s-12c-2s Convolutional neural network %will run 1 epoch in about 200 second and get around 11% error. %With 100 epochs you'll get around 1.2% errorrand('state',0)cnn.layers = { struct('type', 'i') %input layer struct('type', 'c', 'outputmaps', 6, 'kernelsize', 5) %convolution layer struct('type', 's', 'scale', 2) %sub sampling layer struct('type', 'c', 'outputmaps', 12, 'kernelsize', 5) %convolution layer struct('type', 's', 'scale', 2) %subsampling layer};cnn = cnnsetup(cnn, train_x, train_y);opts.alpha = 1;opts.batchsize = 50;opts.numepochs = 1;cnn = cnntrain(cnn, train_x, train_y, opts);[er, bad] = cnntest(cnn, test_x, test_y);%plot mean squared errorfigure; plot(cnn.rL);assert(er<0.12, 'Too big error');```Example: Neural Networks---------------------```matlabfunction test_example_NNload mnist_uint8;train_x = double(train_x) / 255;test_x = double(test_x) / 255;train_y = double(train_y);test_y = double(test_y);% normalize[train_x, mu, sigma] = zscore(train_x);test_x = normalize(test_x, mu, sigma);%% ex1 vanilla neural netrand('state',0)nn = nnsetup([784 100 10]);opts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samples[nn, L] = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.08, 'Too big error');%% ex2 neural net with L2 weight decayrand('state',0)nn = nnsetup([784 100 10]);nn.weightPenaltyL2 = 1e-4; % L2 weight decayopts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samplesnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex3 neural net with dropoutrand('state',0)nn = nnsetup([784 100 10]);nn.dropoutFraction = 0.5; % Dropout fraction opts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samplesnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex4 neural net with sigmoid activation functionrand('state',0)nn = nnsetup([784 100 10]);nn.activation_function = 'sigm'; % Sigmoid activation functionnn.learningRate = 1; % Sigm require a lower learning rateopts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samplesnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex5 plotting functionalityrand('state',0)nn = nnsetup([784 20 10]);opts.numepochs = 5; % Number of full sweeps through datann.output = 'softmax'; % use softmax outputopts.batchsize = 1000; % Take a mean gradient step over this many samplesopts.plot = 1; % enable plottingnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex6 neural net with sigmoid activation and plotting of validation and training error% split training data into training and validation datavx = train_x(1:10000,:);tx = train_x(10001:end,:);vy = train_y(1:10000,:);ty = train_y(10001:end,:);rand('state',0)nn = nnsetup([784 20 10]); nn.output = 'softmax'; % use softmax outputopts.numepochs = 5; % Number of full sweeps through dataopts.batchsize = 1000; % Take a mean gradient step over this many samplesopts.plot = 1; % enable plottingnn = nntrain(nn, tx, ty, opts, vx, vy); % nntrain takes validation set as last two arguments (optionally)[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');```[![Bitdeli Badge](https://d2weczhvl823v0.cloudfront.net/rasmusbergpalm/deeplearntoolbox/trend.png)](https://bitdeli.com/free "Bitdeli Badge")

ARM 内存管理

最早期的计算机,程序是打在卡片上的,CPU 读一张卡片执行一条指令,效率极低。后来有了内存,程序要先加载到内存再执行,也就是 “存储程序” 概念,这才开启了操作系统的发展。1. 单道编程的内存管理2. 多道编程的内存管理:解决 “同时跑多个程序” 的问题为了提升资源利用率,出现了。

qq_52240295的博客 332

jdk-8u144-linux-x64.tar.gz.

该资源为搭建Linux系统Java环境用,资源的后缀为tar.gz格式的压缩包

理解 Linux 动态库加载:LD_LIBRARY_PATH

flyfish

二分掌柜的 345

大中型超市收银系统(可直接运行)

光步前台收银系统系统功能:商品销售、商品退货、挂单、收银员权限、会员销售、单品取消、整单取消、商品查询、脱机销售、脱机数据上传,基本资料下载,开钱箱、小票打印、收款结算,支持多币种付款方式(现金、储值卡、礼券、微信等),支持多种促销。运行环境:.net 4.0登陆信息用户名:1001 密码:123456内置商品信息,商品编码可输入00001000 - 00010000,测试效果相关功能键F5 结算 F9挂单 F11商品查询 F8退货 Insert单品取消 Del整单取消 F12开钱箱F2 会员 Ctrl+Z退出系统 Home 锁屏 相关源码待公开

IMSL CNL 7.0.0 (x86-64)Crack

IMSL CNL 7.0.0 (x86-64)Crack intel的算法库破解文件,这是C++版本的破解文件

Linux-iostat命令详解

Linux命令学习记录

m0xin的博客 111

Linux 服务器性能排查手册(2026):CPU、内存、磁盘IO、网络四大瓶颈定位

iptables 四表五链模型、firewalld zone 信任级别、云安全组与主机防火墙的关系与优先级,避坑改了防火墙把自己挡在服务器外面的翻车事故。

2502_91473995的博客 317

【Linux】APT 本地 deb 安装与 `-f` 参数总结笔记

apt install ./xx.deb 可自动解析并安装依赖,无需 -f;-f 仅用于修复已损坏的依赖状态,非首次安装时必需。apt install -f 可单独运行,修复 broken dependencies。两者职责不同:前者是安装与依赖解决,后者是故障修复。完全离线时需提前准备依赖包或本地源。

hknaruto的专栏 211

Linux rm 误删文件恢复实操教程

Linux使用rm删除文件时,并不会直接抹除磁盘上的数据,只是移除文件索引,让系统不再识别这块空间。只要没有写入新数据,原有扇区内容就会保留。新文件写入才有可能覆盖这些区域,一旦覆盖就很难找回。恢复的本质就是扫描磁盘,找到这些还存在、但索引丢失的数据条目,再把它们导出保存到其他分区。越早停止写入,恢复成功的概率越高。

海天数据恢复-winhex数据恢复教程 228

Linux sudo

如果输出 → 无 sudo 权限 如果输出 → 拥有全部 sudo 权限 辅助验证命令 ⚠️ 注意:在 wheel 组 ≠ 一定能 sudo,必须 开启 Ubuntu/Debian: ✅ 重要:修改组之后,用户要重新登录才生效! 或者执行 临时生效 看到这行(没有 #注释)才生效: 方式 2:visudo 直接单独给用户授权(精细化权限) 找到 ,下面添加一行: 自带语法校验,写错会告警,不要直接 vim 改 ,写错直接 sudo 炸掉! 想免密 su

fengliyang_的博客 178

Windows/Linux下强实时运动控制内核(二):基于Qt的Delta机械手的开发应用

强实时运动控制内核MotionRT750下Qt开发Delta机械手的完整开发流程。

weixin_57350300的博客 241

Linux epoll 一篇讲透:从 select/poll 到红黑树、LT/ET,再到完整 TCP 服务器

一万个客户端已经连上服务器,眼下只有十个客户端发来了数据。服务器怎样把时间花在这十个连接上?理解这个问题,就抓住了 epoll 的主线。接下来,我们沿着“为什么需要它 → 接口怎么用 → 内核如何实现 → LT/ET 怎么写 → 完整服务器怎么运行”的顺序,把知识连起来。**阅读基础:**了解socketbindlistenaccept的基本用途即可。本文示例面向 Linux,服务器使用 C++17,实验脚本使用 Python 3。

2601_94861874的博客 164

Linux 网络基础详解:IP、子网、路由与 ip、ss 命令实战

建库建表、增删改查、连接查询(内连左连右连)、聚合函数、权限控制 GRANT/REVOKE,每条命令配可运行示例,零基础也能跟着敲会 SQL 基础。

2502_91473995的博客 615

Linux、Shell、MySQL 测试卷逐题细讲(下篇:MySQL)

本文为Linux、Shell、MySQL测试卷下半段MySQL部分逐题讲解,包含填空、选择与SQL分析三类题型。填空题覆盖COUNT、HAVING、DISTINCT、事务、约束、索引等核心语法;选择题辨析存储过程、索引类型、ACID、存储引擎、用户管理等考点。SQL大题围绕员工、部门、职位、地点四张关联表,考察多表连接、分组聚合、自连接、相关子查询、NULL处理等高频写法,标注LEFT JOIN统计计数、NULL判断、子查询别名等易错坑点,同时梳理试卷OCR识别带来的干扰问题,重点提示SQL实操中的常见失误

dongziwen1的博客 183
上一篇: Linux内核学习轨迹第五部:缺页异常处理全链路深度解析(第七小节)
下一篇: 蓝牙安全漏洞:这些配对模式必须禁用
WythePlus
博客等级 码龄11年 397粉丝 300原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值