实验六 基于Python的数字图像压缩算法
一、实验目的
掌握图像压缩的必要性;
掌握常见的图像压缩标准;
掌握常见的图像压缩方法分类;
掌握常见的图像压缩方法原理与实现(包括哈夫曼编码、算术编码、行程编码方法等);
了解我国音视频编解码标准的发展。
二、实验内容
- 学习图像压缩章节内容。
- 读取灰度图像cameraman.jpg和barbara.jpg,从以下方法中选择两种实现对图像的压缩,并显示压缩比和压缩前后对比图像,试分析所选算法的优缺点。
A.哈夫曼编码; B. 算术编码; C. 行程编码;D. 小波图像编码。
三、完整实验程序、结果与分析
- 图像压缩是通过减少图像数据的冗余性来实现高效存储与传输的关键技术,其核心目标是在保证视觉质量的前提下降低数据量。根据压缩后信息是否完整保留,可分为无损压缩和有损压缩两类。
无损压缩基于统计冗余(如哈夫曼编码、行程编码),通过构建最优编码表将高频像素值用短码表示,实现精确还原但压缩比有限(通常2:1~3:1),适用于医学影像、工程制图等对精度要求严格的场景。
有损压缩则利用人类视觉特性(如小波编码、JPEG),通过傅里叶变换、小波变换等频域分析分离高频细节与低频主体,结合量化和阈值处理舍弃次要信息,可获得10:1以上的高压缩比,广泛用于网络图像传输和视频流媒体。
其中,哈夫曼编码通过贪心算法构建最优前缀码树,实现信息熵极限压缩,但需额外存储码表;小波编码通过多分辨率分析实现图像分层压缩,在保留主体特征的同时显著减少数据量,但会引入振铃效应等失真。不同算法在压缩效率、重建质量和计算复杂度上存在显著差异,实际应用需根据场景需求权衡选择。 - 选择A.哈夫曼编码和D. 小波图像编码
代码
显示压缩比和压缩前后对比图像,试分析所选算法的优缺点。
哈夫曼编码
压缩比: 通常较低(约1.2-1.5倍),因为自然图像像素分布均匀,且需存储编码表。
优点: 无损压缩,精确还原图像。
缺点: 压缩比低,不适合高压缩需求场景,存储编码表增加额外开销。
小波编码
压缩比: 较高(可达5-10倍),通过去除高频细节实现。
优点: 高压缩比,保留主要视觉特征。
缺点: 有损压缩,高频细节丢失,图像可能出现模糊。
对比结论
哈夫曼编码适用于需要无损压缩的场景(如医学图像),但压缩效率有限。
小波编码适用于允许有损压缩的高效存储(如网络传输),但会损失部分细节。
四、问题及心得
在本次实验中,主要遇到图像读取失败及压缩算法实现问题。读取barbara.jpg
时因路径格式错误导致加载失败,经排查发现路径需使用原始字符串(r"..."
)避免转义,并通过os.path.exists
验证路径存在性。此外,文件实际格式与扩展名不符时,OpenCV无法读取,改用PIL库并添加文件头校验后解决。压缩算法方面,哈夫曼编码因像素分布均匀导致压缩比低(约1.3倍),且编码表存储开销大;小波编码通过阈值量化高频分量实现高压缩比(约5倍),但重构图像出现边缘模糊。实验表明,无损压缩(哈夫曼)适合精度要求高的场景,而有损压缩(小波)更适用于存储优化。此次实践深化了对路径处理、文件格式验证及压缩算法特性的理解,同时认识到错误隔离和模块化测试的重要性。
完整代码
import cv2
import numpy as np
import matplotlib.pyplot as plt
import pywt
from heapq import heappush, heappop, heapifyimport os
from PIL import Imageclass HuffmanCoder:def __init__(self):self.codes = {}def _build_heap(self, freq):heap = [[weight, [pixel, ""]] for pixel, weight in freq.items()]heapify(heap)while len(heap) > 1:lo = heappop(heap)hi = heappop(heap)for pair in lo[1:]:pair[1] = '0' + pair[1]for pair in hi[1:]:pair[1] = '1' + pair[1]heappush(heap, [lo[0] + hi[0]] + lo[1:] + hi[1:])return heap[0] if heap else []def _build_codes(self, heap_entry):codes = {}for pair in heap_entry[1:]:pixel, code = paircodes[pixel] = codereturn codesdef encode(self, data):freq = {}for pixel in data.flatten():freq[pixel] = freq.get(pixel, 0) + 1if not freq:return ""heap_entry = self._build_heap(freq)if not heap_entry:return ""self.codes = self._build_codes(heap_entry)encoded_data = ''.join([self.codes[pixel] for pixel in data.flatten()])return encoded_datadef decode(self, encoded_data, shape):inv_codes = {v: k for k, v in self.codes.items()}current_code = ""decoded_pixels = []for bit in encoded_data:current_code += bitif current_code in inv_codes:decoded_pixels.append(inv_codes[current_code])current_code = ""return np.array(decoded_pixels, dtype=np.uint8).reshape(shape)def compress_huffman(img):coder = HuffmanCoder()encoded_data = coder.encode(img)data_bits = len(encoded_data)table_bits = 0for pixel, code in coder.codes.items():table_bits += 8 + 4 + len(code)total_bits = data_bits + table_bitsdecoded_img = coder.decode(encoded_data, img.shape)return decoded_img, total_bitsdef compress_wavelet(img, threshold=10.0, quant_factor=20):coeffs = pywt.wavedec2(img, 'haar', level=1)coeff_arr, coeff_slices = pywt.coeffs_to_array(coeffs)coeff_arr_thresh = coeff_arr.copy()coeff_arr_thresh[np.abs(coeff_arr_thresh) < threshold] = 0quantized = np.round(coeff_arr_thresh * quant_factor).astype(np.int32)non_zero = quantized != 0non_zero_coords = np.transpose(np.nonzero(non_zero))non_zero_values = quantized[non_zero]num_non_zero = len(non_zero_values)total_bits = num_non_zero * (16 + 32)dequantized = non_zero_values.astype(np.float32) / quant_factorrecon_coeff_arr = np.zeros_like(coeff_arr, dtype=np.float32)recon_coeff_arr[non_zero] = dequantizedrecon_coeffs = pywt.array_to_coeffs(recon_coeff_arr, coeff_slices, output_format='wavedec2')reconstructed = pywt.waverec2(recon_coeffs, 'haar')reconstructed = np.clip(reconstructed, 0, 255).astype(np.uint8)return reconstructed, total_bitsdef plot_images(original, reconstructed, title, compression_ratio):plt.figure(figsize=(10, 5))plt.subplot(1, 2, 1)plt.imshow(original, cmap='gray')plt.title('Original Image')plt.axis('off')plt.subplot(1, 2, 2)plt.imshow(reconstructed, cmap='gray')plt.title(f'{title}\nCR: {compression_ratio:.2f}')plt.axis('off')plt.show()def safe_imread(path):# 基础路径验证if not os.path.exists(path):print(f"❌ 路径不存在: {path}")print("可能原因:")print(f"1. 请检查D盘是否存在")print(f"2. 确认完整路径:{os.path.abspath(path)}")return None# 文件权限检查if not os.access(path, os.R_OK):print(f"⛔ 无读取权限: {path}")return None# 文件大小检查file_size = os.path.getsize(path)if file_size < 1024:print(f"⚠️ 文件过小({file_size}字节),可能已损坏: {path}")# 尝试用OpenCV读取img = cv2.imread(path, cv2.IMREAD_GRAYSCALE)if img is not None:return imgtry:print(f"⚠️ OpenCV读取失败,尝试PIL读取: {path}")pil_img = Image.open(path).convert('L')return np.array(pil_img, dtype=np.uint8)except Exception as e:print(f"❌ 双重读取均失败: {path}")print(f"错误详情: {str(e)}")# 文件头验证with open(path, 'rb') as f:header = f.read(4).hex()print(f"📄 文件头(十六进制): {header}")print("正常JPEG应以 ffd8ff 开头")return Nonedef main():img_paths = [r"D:\tuxiang\cameraman.jpg", # 使用原始字符串r"D:\tuxiang\barbara.jpg",]for path in img_paths:print(f"\n{'=' * 40}\n处理图像: {path}")# 安全读取图像img = safe_imread(path)if img is None:print("跳过处理...")continue# 显示基本信息print(f"✅ 成功读取 | 尺寸: {img.shape} | 数据类型: {img.dtype}")# 哈夫曼编码try:huff_img, huff_bits = compress_huffman(img)cr_huff = (img.size * 8) / huff_bits if huff_bits != 0 else 0plot_images(img, huff_img, 'Huffman Encoding', cr_huff)except Exception as e:print(f"哈夫曼编码错误: {str(e)}")# 小波编码try:wavelet_img, wavelet_bits = compress_wavelet(img)cr_wavelet = (img.size * 8) / wavelet_bits if wavelet_bits != 0 else 0plot_images(img, wavelet_img, 'Wavelet Encoding', cr_wavelet)except Exception as e:print(f"小波编码错误: {str(e)}")if __name__ == "__main__":main()
相关文章:
实验六 基于Python的数字图像压缩算法
一、实验目的 掌握图像压缩的必要性; 掌握常见的图像压缩标准; 掌握常见的图像压缩方法分类; 掌握常见的图像压缩方法原理与实现(包括哈夫曼编码、算术编码、行程编码方法等); 了解我国音视…...
Vue 3 中的 nextTick 使用详解与实战案例
Vue 3 中的 nextTick 使用详解与实战案例 在 Vue 3 的日常开发中,我们经常需要在数据变化后等待 DOM 更新完成再执行某些操作。此时,nextTick 就成了一个不可或缺的工具。本文将介绍 nextTick 的基本用法,并通过三个实战案例,展示…...
Docker + Watchtower 实现容器自动更新:高效运维的终极方案
文章目录 前言一、Watchtower 简介二、Watchtower 安装与基本使用1. 快速安装 Watchtower2. 监控特定容器 三、Watchtower 高级配置1. 设置检查间隔2. 配置更新策略3. 清理旧镜像4. 通知设置 四、生产环境最佳实践1. 使用标签控制更新2. 更新前执行健康检查3. 结合CI/CD流水线 …...
OpenCV 中用于背景分割(背景建模)的一个类cv::bgsegm::BackgroundSubtractorGSOC
操作系统:ubuntu22.04 OpenCV版本:OpenCV4.9 IDE:Visual Studio Code 编程语言:C11 算法描述 cv::bgsegm::BackgroundSubtractorGSOC 是 OpenCV 中用于背景分割(背景建模)的一个类,它是基于 GMMÿ…...
AI恶魔之眼使用说明书
AI恶魔之眼使用说明书 产品简介 1.1 产品介绍 AI恶魔之眼是一款具备动态视觉效果与仿生眼睛模拟功能的智能显示产品,可实现以下特性: 真实人眼模拟:支持虹膜样式变换、眨眼动画、瞳孔缩放等动态特效,仿真度高自定义内容上传&am…...
PBR材质-Unity/Blender/UE
目录 前言: 一、Unity: 二、Blender: 三、UE: 四、全家福: 五、后记: 前言: PBR流程作为表达物理效果的经典方式,很值得一学。纹理贴图使用的是上一期的Textures | cgbookcas…...
C++复习
线程库(类) 在C11之前,涉及到多线程问题,都是和平台相关的,比如Windows和Linux下各有自己的接口,这使得代码的可移植性比较差。C11中最重要的特性就是对线程进行了支持,使得C在并行编程时不需要依赖第三方…...
如何使用docker配置ros-noetic环境并使用rviz,gazebo
参考链接:【Ubuntu】Docker中配置ROS并可视化Rviz及Gazebo_docker ros-CSDN博客 前言: 其实这个东西是相当必要的,因为我们有时候需要在一台电脑上跑好几个项目,每个项目都有不同的依赖,这些依赖冲突搞得人头皮发麻&…...
计算机网络中相比于RIP,路由器动态路由协议OSPF有什么优势?
好的!以下是关于路由信息协议(RIP,Routing Information Protocol)的技术原理详解,以及其与OSPF(Open Shortest Path First)的对比分析。内容分为技术原理、对比优势和不足两部分。 一、RIP技术原理深度解析 1. 基本概念 协议类型:RIP属于距离向量路由协议(Distance-V…...
相似命令对比
awk 命令用法表格 场景命令示例说明示例输入文件内容 (input.txt)输出结果1. 基础字段提取awk -F: {print $1} /etc/passwd按分隔符提取第1列(如用户名)。root:x:0:0:root:/root:/bin/bashroot2. 多字段组合输出awk -F: {print $1, $3, $7} /etc/passwd…...
Vuerouter 的底层实现原理
文章目录 前言🧩 Vue Router 底层实现核心原理🧠 执行流程图(简化版)🔍 核心模块源码原理(简要)① 路由注册与匹配(createRouterMatcher)② 历史模式管理器(c…...
按拼音首字母进行排序组成新的数组(vue)
数据按首字母相同的组成新的数组,使用拼音(Pinyin)转换 比如想要的效果: 下载 npm install pinyin代码: import pinyin from "pinyin"; let studentAllList [{onLine: true,points: undefined…...
在IPv6头部中,Next Header字段
在IPv6头部中,Next Header字段 在IPv6头部中,Next Header字段是一个8位的字段,它的作用是指示下一个头部扩展的类型或者最终的传输层协议类型。这个字段的值决定了数据包中紧随IPv6头部之后的头部扩展的类型,或者是直接指向传输层…...
vue项目部署后部分子页面刷新后403
经过我的仔细分析;终于找到了是刷新后路径后面自动拼接了 / ;如 66.66.66.66/aPage 刷新后变成了 66.66.66.66/aPage/ 导致403 方法一: 修改路由为hash模式 // router/index.jsimport { createRouter, createWebHistory, createWebHashHist…...
C# NX二次开发:曲线和点位相关UFUN函数详解
大家好,今天要介绍查询曲线上点位和返回沿着曲线偏移一定距离的UFUN函数。 (1)UF_MODL_ask_curve_points:这个函数的定义为按照给定条件查询曲线上的点位。 Defined in: uf_modl_curves.h Overview Returns an array of 3D …...
服务器数据恢复—硬盘坏道导致EqualLogic存储不可用的数据恢复
服务器存储数据恢复环境&故障: 一台EqualLogic某型号存储中有一组由16块SAS硬盘组建的RAID5阵列。上层采用VMFS文件系统,存放虚拟机文件,上层一共分了4个卷。 磁盘故障导致存储不可用,且设备已经过保。 服务器存储数据恢复过程…...
【2019 CWE/SANS 25 大编程错误清单】12越界写入
案例1: void tonly_aw21036_led_drv_pwm_init(tonly_gpio_pin_t gpio_pin, uint8_t pwm) {uint8_t pin gpio_pin - AW21036_GPIO_PIN_START;if (pin < AW21036_LED_MAX_CHANNEL){aw21036_ctx.pwm[pin] pwm; /* 有效通道号: 0-35 */}else{TONLY_LED_LOG_E(&qu…...
redis bitmap数据类型调研
一、bitmap是什么? redis原文: Bitmaps are not an actual data type, but a set of bit-oriented operations defined on the String type . This means that bitmaps can be used with string commands, and most importantly with SET and GET. 翻…...
[Windows] Ghost Downloader v3.5.9 开源多线程下载工具
[Windows] Ghost Downloader 链接:https://pan.xunlei.com/s/VOPejV3veb6v-im-wVmMkXkhA1?pwdpzwk# Ghost Downloader 是一款专为Windows平台设计的多线程下载工具,完全由Python语言开发。它以其高效的多线程下载技术和断点续传功能而著称,…...
互联网大厂Java求职面试:AI集成与云原生架构设计
互联网大厂Java求职面试:AI集成与云原生架构设计 面试场景:技术总监与程序员郑薪苦的对话 技术总监:郑薪苦,我们今天来聊聊你在AI集成场景中的经验。你有没有尝试过将Spring AI与大模型结合? 郑薪苦:有啊…...
gitignore的相关用法
gitignore .gitignore 是 git 用于管理需要忽略追踪的文件。.gitignore 一般用于远程仓库多人协作的场景,最常见的情况是,使用 MacOS 系统的程序员要在 .gitignore 中添加 .DS_Store 防止将其推送至仓库中。或在开发代码时,将调试文件忽略&a…...
前端取经路——工程化渡劫:八戒的构建之道
大家好,我是老十三,一名前端开发工程师。前端工程化就像八戒的钉耙,看似简单却能降妖除魔。在本文中,我将带你探索前端工程化的九大难题,从模块化组织到CI/CD流程,从代码规范到自动化测试,揭示这些工具背后的核心原理。无论你是初学者还是资深工程师,这些构建之道都能帮…...
Android 数据持久化之 Room 数据库存储
一、简介 Room 是 Google 推出的 Android 持久层框架,建立在 SQLite 之上,提供了一个抽象层,简化了数据库操作。它通过注解和编译时检查来确保数据操作的正确性。 Room 主要由以下三个组件组成: Entity(实体):定义封装实际数据的实体类,每个实体类对应数据库中的一个…...
Selenium Web自动化测试学习笔记(一)
自动化测试 技术手段模拟人工,执行重复性任务,准确率100%,高于人工 selenium 可通过浏览器驱动控制浏览器,通过元素定位模拟人工,实现web自动化,没有焦点(把浏览器放在最小化依然可以&#x…...
一个项目的周测试的文档(Billing Service 测试文档)
目录 Pending Pool 各项功能测试... 2 1. Assign 分配功能。测试结果: ok. 2 2. Reset 功能。 测试结果: OK. 3 3. Discard 功能。测试结果: 提示discard成功,但是historical job没有找到记录... 3 4. E…...
二分查找习题
一、二叉搜索树与双向链表(剑指 Offer JZ36 ) 解题思路要点 - 利用中序遍历特性:二叉搜索树的中序遍历结果是有序序列,这是将二叉搜索树转化为有序双向链表的关键。通过中序遍历可以按从小到大的顺序访问节点,满足…...
JumpServer批量添加资产
环境说明:我的环境是H3C网络设备环境 一、在linux系统环境下通过Python脚本获取交换机信息,IP地址和设备名称一一对应,脚本如下: cat get_device-sysname.py import re from netmiko import ConnectHandler from concurrent.fut…...
使用 Python 与 Java 实现接入 AI 大模型的 MCP 协议:原理与实战
一、什么是 MCP 协议? MCP(Model Context Protocol) 是一种专为远程控制和管理 AI 大模型而设计的通信协议。它允许客户端通过网络向服务器发送请求,以执行诸如模型推理、状态查询、参数更新等操作,并接收相应的结果。…...
Nginx核心原理以及案例分析(AI)
一、Nginx核心原理分析 1. 事件驱动与非阻塞模型 Epoll异步机制:基于Linux的epoll模型实现异步非阻塞I/O处理,单线程可高效管理数万并发连接,避免传统select模型的轮询性能瓶颈。多进程架构:采用Master-Worker模式&…...
ChromeDriverManager的具体用法
ChromeDriverManager 是 webdriver_manager 库的一部分,它用于自动管理 ChromeDriver 的下载和更新。使用 ChromeDriverManager 可以避免手动下载 ChromeDriver 并匹配系统中安装的 Chrome 浏览器版本。以下是 ChromeDriverManager 的基本用法: 步骤 1…...
Linux:认识基础IO
1.理解"⽂件" 1.1狭义理解 ⽂件在磁盘⾥ 磁盘是永久性存储介质,因此⽂件在磁盘上的存储是永久性的 磁盘是外设(即是输出设备也是输⼊设备) 磁盘上的⽂件 本质是对⽂件的所有操作,都是对外设的输⼊和输出 简称 IO 1.2广…...
SimpleMindMap:一个支持AI的思维导图软件
SimpleMindMap(思绪思维导图)是一款开源、跨平台且功能丰富的思维导图工具,支持 Web 端及多平台客户端(Windows、macOS、Linux)。 SimpleMindMap 提供的主要功能如下: 插件化设计,除了核心功能…...
数据库故障排查指南:MySQL 解决常见问题解决
数据库是现代 IT 系统的核心引擎,承载着企业最重要的数据资产。数据库的稳定、高效运行直接关系到业务的生死存亡。然而,由于软硬件、配置、应用访问等多种因素的影响,数据库故障难以完全避免。当故障发生时,能够迅速定位、分析并解决问题,同时确保数据安全不受影响,是每…...
2025年特种作业操作证考试题库及答案(登高架设作业)
一、单选题 202.带电跨越架羊角撑杆高度( )m。 A.1 B.1.1 C.1.2 答案:B 203.跨越架拉线地锚埋深必须按( )及架体设计要求进行。 A.现场情况决定 B.土质情况 C.地锚设计分坑图 答案:C 204.单排脚手架洞口处&#…...
Open CASCADE学习|ApplicationFramework 框架使用指南
在现代 CAD(计算机辅助设计)应用开发中,构建一个高效、可扩展且用户友好的应用程序框架是至关重要的。Open CASCADE(简称 OCC)提供了一个功能强大的 ApplicationFramework(应用程序框架)&#x…...
hadoop中的序列化和反序列化(3)
3. Java的序列化 Java提供了内置的序列化机制,通过java.io.Serializable接口实现。 3.1 如何实现Java序列化 让类实现Serializable接口。 使用ObjectOutputStream进行序列化。 使用ObjectInputStream进行反序列化。 示例代码 序列化 java 复制 import jav…...
PostgreSQL给新用户授权select角色
✅ 切换到你的数据库并以超级用户登录(例如 postgres): admin#localhost: ~$ psql -U postgres -d lily✅ 创建登录的账号机密吗 lily> CREATE USER readonly_user WITH PASSWORD xxxxxxxxxxx; ✅ 确认你授予了这个表的读取权限…...
MySQL 8.0 OCP(1Z0-908)英文题库(1-10)
目录 第1题题目解析正确答案 第2题题目解析正确答案 第3题题目解析正确答案 第4题题目解析正确答案 第5题题目解析正确答案 第6题题目解析正确答案 第7题题目解析正确答案 第8题题目解析正确答案 第9题题目解析正确答案 第10题题目解析正确答案: 第1题 Your MySQL …...
南京市出台工作方案深化“智改数转网联”,物联网集成商从“困局”到“蓝海”!
为落实《江苏省深化制造业智能化改造数字化转型网络化联接三年行动计划(2025-2027年)》,南京市近日出台“工作方案”,部署五大行动17项重点任务,进一步深化全市制造业智能化改造、数字化转型、网络化联接(以…...
系统思考:教育焦虑恶性循环分析
今天和团队的小伙伴一起拆解了一个父母教育焦虑与报班行为之间的系统环路图,报班越多 ➡ 孩子自由时间越少 ➡ 情绪调节力下降 ➡ 学习效率更低 ➡ 成绩不理想 ➡ 家长更焦虑 ➡ 继续加码报班…… 一圈一圈,像是陷入了“焦虑的恶性循环”。 这也是我一直…...
(已完结)完美解决C盘拓展卷是灰色的无法扩容的问题以及如何正确地在WINDOS上从一个盘扩容到C盘
众所周知,window系统在“计算机”管理中自带了一个磁盘管理系统 但是在使用过程中会出现各种各样无法扩容的毛病。 第一:首先排查,大多数人在扩容之前忽视了一点就是,我们现代的很多新机器都是默认开启BitLocker加密的ÿ…...
优选算法系列(8.多源BFS)
简介: 01 矩阵(medium): 题目链接:542. 01 矩阵 - 力扣(LeetCode) 算法: 对于求的最终结果,我们有两种方式: 第⼀种方式:从每⼀个 1 开始&#…...
迈向AI辅助数据分析代码生成的透明性与知识共享
李升伟 摘译 生成式人工智能(AI)及尤其大型语言模型(LLMs)正在改变我们进行数据科学研究的方式. 最显著的例子包括科学家使用该技术与科学数据交互, 回答数据分析问题, 生成数据分析代码以及(重新)撰写科研手稿. 然而遗憾的是&am…...
autojs和冰狐智能辅助该怎么选择?
最近打算做自动化脚本,在autojs和冰狐智能辅助中做选择,不知道该怎么选。没办法只能花费大量时间仔细研究了autojs和冰狐智能辅助,综合考虑功能需求、开发复杂度、编程经验及项目规模等因素。以下是两者的核心对比及选择建议,仅供…...
小数的二进制表示
相信很多人都知道整数的二进制表示方法,但是小数的二进制就不一定了。 想来简单说一下整数的,就是不断的除以2取余数, 大致这样 从下往上取,这里42的结果就是101010 而且每个整数都有他对应的二进制数,但是小数转二…...
信息系统项目管理师-软考高级(软考高项)2025最新(十)
个人笔记整理---仅供参考 第十章项目进度管理 10.1管理基础 10.2项目进度管理过程 10.3规划进度管理 10.4定义活动 选C 10.5排列活动顺序 10.6估算活动持续时间 10.7制订进度计划 制订进度计划4个步骤(背,案例可能会考!) 10.8控制…...
Linux内核初始化机制全解析:从pure_initcall到late_initcall
引言 Linux内核的启动过程是一个高度有序的初始化流程,涉及数百个模块和子系统的协同工作。为了确保依赖关系正确、硬件资源按需分配,内核通过一系列初始化宏(如pure_initcall、subsys_initcall、late_initcall等)将函数划分为不同的优先级,按严格顺序执行。本文将深入探…...
pcie协议复位
pcie协议复位共有4中情况;cold reset;warm reset;hot reset;function level reset; 分类: 依据spec 6.6: Conventional reset(传统复位):cold,…...
boost笔记: Cannot open include file: ‘boost/mpl/aux_/preprocessed/plain/.hpp‘
1. 问题描述 因为一下库定义了宏and,导致boost的文件包含and.hpp展开成&.hpp,所以出现以下错误 Cannot open include file: ‘boost/mpl/aux_/preprocessed/plain/&.hpp’ 2. 解决方案 在定义宏之前包含boost文件,但这种方案的缺点…...
Xilinx XCKU11P-2FFVA1156I 赛灵思 FPGA AMD Kintex UltraScale+
XCKU11P-2FFVA1156I 属于 AMD Kintex UltraScale™ FPGA 家族,采用 TSMC 20 nm FinFET 工艺,兼顾高性能与功耗效率,提供约 653 100 个逻辑单元、2 928 个 DSP 切片、21.1 Mb Block RAM 和 22.5 Mb UltraRAM,可广泛应用于网络加速、…...