# 基于词袋模型(BoW)的猫狗图像分类实践
基于词袋模型(BoW)的猫狗图像分类实践
在计算机视觉领域,图像分类是一项基础且重要的任务。本文将介绍如何使用词袋模型(Bag of Words, BoW)结合支持向量机(SVM)实现猫狗图像分类。通过详细的代码实现和过程分析,帮助读者快速掌握这一经典方法的应用。
一、背景知识
(一)词袋模型(BoW)
词袋模型是一种用于文本分类的模型,它将文本中的单词看作是“词袋”中的元素,忽略单词的顺序和语法结构,只关注单词的出现频率。在图像处理中,我们可以将图像中的局部特征(如 SIFT 特征)看作是“词”,通过聚类将这些特征划分为不同的“视觉单词”,然后统计每个图像中各个视觉单词的出现频率,形成词袋直方图,作为图像的特征表示。
(二)支持向量机(SVM)
支持向量机是一种强大的分类算法,它通过寻找最优分割超平面,将不同类别的数据分隔开。在图像分类任务中,SVM 可以根据图像的特征向量进行分类,具有良好的分类性能和泛化能力。
二、代码实现
(一)环境准备
在开始之前,请确保已安装以下 Python 库:
- OpenCV:用于图像处理和特征提取。
- scikit-learn:用于机器学习算法的实现,包括 KMeans 聚类和 SVM 分类。
- NumPy:用于数值计算。
可以通过以下命令安装这些库(如果尚未安装):
pip install opencv-python scikit-learn numpy
(二)代码解析
1. 类定义与初始化
class BowClassifier:def __init__(self, num_clusters=100):self.num_clusters = num_clustersself.kmeans = KMeans(n_clusters=num_clusters, random_state=42)self.svm = SVC(kernel='linear', probability=True, random_state=42)self.sift = cv2.SIFT_create()self.scaler = StandardScaler()self.class_names = ['cat', 'dog'] # 确保与文件夹名称一致
num_clusters
:词袋模型中视觉单词的数量。kmeans
:用于将 SIFT 特征聚类为视觉单词。svm
:用于分类的 SVM 模型。sift
:用于提取图像的 SIFT 特征。scaler
:用于对特征进行标准化处理。class_names
:类别名称,这里以猫和狗为例。
2. 特征提取
def extract_features(self, image):"""使用SIFT提取图像特征"""try:gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)keypoints, descriptors = self.sift.detectAndCompute(gray, None)return descriptorsexcept Exception as e:print(f"特征提取错误: {e}")return None
- 将图像转换为灰度图像。
- 使用 SIFT 算法提取图像的特征点和描述符。
- 如果提取过程中出现错误,返回
None
。
3. 数据加载与特征提取
def load_dataset(self, data_dir):"""加载数据集并提取特征"""features = []labels = []processed_count = 0failed_count = 0# 验证数据目录是否存在if not os.path.exists(data_dir):raise FileNotFoundError(f"数据目录 {data_dir} 不存在")for class_idx, class_name in enumerate(self.class_names):class_dir = os.path.join(data_dir, class_name)# 验证类别目录是否存在if not os.path.exists(class_dir):print(f"警告: 类别目录 {class_dir} 不存在,跳过")continueprint(f"\n正在处理类别: {class_name} ({class_dir})")for img_name in sorted(os.listdir(class_dir)):img_path = os.path.join(class_dir, img_name)# 添加更严格的图像格式检查if not img_name.lower().endswith(('.jpg', '.jpeg', '.png', '.bmp')):print(f"跳过非图像文件: {img_name}")continuetry:# 使用更可靠的图像读取方式with open(img_path, 'rb') as f:file_bytes = np.asarray(bytearray(f.read()), dtype=np.uint8)image = cv2.imdecode(file_bytes, cv2.IMREAD_COLOR)if image is None:print(f"警告: 无法解码图像 {img_name},可能已损坏")failed_count += 1continue# 检查图像尺寸是否合理if image.shape[0] < 32 or image.shape[1] < 32:print(f"警告: 图像 {img_name} 尺寸过小 ({image.shape}),跳过")failed_count += 1continue# 提取特征descriptors = self.extract_features(image)if descriptors is None or len(descriptors) == 0:print(f"警告: 图像 {img_name} 未检测到特征点,跳过")failed_count += 1continuefeatures.append(descriptors)labels.append(class_idx)processed_count += 1if processed_count % 20 == 0:print(f"已处理 {processed_count} 张图像...")except Exception as e:print(f"处理图像 {img_name} 时出错: {str(e)}")failed_count += 1print(f"\n特征提取完成,共 {processed_count} 个有效样本")print(f"失败/跳过 {failed_count} 个样本")if processed_count == 0:raise ValueError("没有提取到任何有效特征,请检查:\n""1. 图像文件是否真实存在\n""2. 文件路径是否包含特殊字符\n""3. 图像文件是否已损坏\n""4. 文件权限是否正确")return features, labels
- 遍历数据目录中的每个类别文件夹。
- 对每个图像文件进行读取和特征提取。
- 跳过非图像文件、损坏的图像文件、尺寸过小的图像文件以及未检测到特征点的图像文件。
- 将提取到的特征和对应的标签存储起来。
4. 创建词袋直方图
def create_bow_histograms(self, features):"""创建词袋直方图"""histograms = []for descriptor in features:clusters = self.kmeans.predict(descriptor)histogram = np.bincount(clusters, minlength=self.num_clusters)histograms.append(histogram)return np.array(histograms)
- 对每个图像的特征描述符进行聚类,得到每个描述符所属的聚类中心(即视觉单词)。
- 统计每个图像中各个视觉单词的出现频率,形成词袋直方图。
5. 模型训练与评估
def train(self, data_dir):"""训练模型"""print("开始加载数据集和提取特征...")start_time = time.time()try:# 1. 加载数据集并提取特征features, labels = self.load_dataset(data_dir)# 2. 将所有描述符连接起来用于K-means聚类print("\n开始合并特征描述符...")all_descriptors = np.vstack(features)print(f"合并完成,总描述符数量: {all_descriptors.shape[0]}")# 3. 训练K-means聚类器print(f"\n开始K-means聚类 ({self.num_clusters}个聚类中心)...")self.kmeans.fit(all_descriptors)print("K-means聚类完成")# 4. 为每个图像创建词袋直方图print("\n创建词袋直方图...")X = self.create_bow_histograms(features)y = np.array(labels)# 5. 标准化特征X = self.scaler.fit_transform(X)# 6. 分割训练集和测试集X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.1, random_state=42, stratify=y)print(f"\n训练集: {X_train.shape[0]} 个样本")print(f"测试集: {X_test.shape[0]} 个样本")# 7. 训练SVM分类器print("\n开始训练SVM分类器...")self.svm.fit(X_train, y_train)print("SVM训练完成")# 8. 评估模型print("\n评估模型性能...")y_pred = self.svm.predict(X_test)precision = precision_score(y_test, y_pred, average='weighted')recall = recall_score(y_test, y_pred, average='weighted')f1 = f1_score(y_test, y_pred, average='weighted')print("\n分类报告:")print(classification_report(y_test, y_pred, target_names=self.class_names))print(f"\n测试集评估结果:")print(f"Precision: {precision:.4f}")print(f"Recall: {recall:.4f}")print(f"F1-score: {f1:.4f}")except Exception as e:print(f"\n训练过程中发生错误: {str(e)}")finally:end_time = time.time()print(f"\n总耗时: {end_time - start_time:.2f}秒")
- 将数据集分为训练集和测试集,测试集占总数据集的 10%。
- 使用训练集训练 SVM 分类器。
- 在测试集上评估模型性能,计算精确率(Precision)、召回率(Recall)和 F1 分数,并打印分类报告。
- 最后,打印整个训练和评估过程的总耗时。
(三)主函数
if __name__ == "__main__":# 使用原始字符串处理路径,避免转义问题data_dir = r"D:\Users\妄生\PycharmProjects\人工智能\作业(2023)\data"# 创建并训练分类器try:print("=" * 50)print("开始猫狗图像分类任务")print("=" * 50)# 先验证数据目录if not os.path.exists(data_dir):raise FileNotFoundError(f"主数据目录不存在: {data_dir}")print("\n数据目录结构验证:")for class_name in ['cat', 'dog']:class_dir = os.path.join(data_dir, class_name)if os.path.exists(class_dir):num_images = len([f for f in os.listdir(class_dir) if f.lower().endswith(('.jpg', '.jpeg', '.png'))])print(f"{class_name}目录: {class_dir} (包含 {num_images} 张图像)")else:print(f"警告: {class_name}目录不存在: {class_dir}")bow_classifier = BowClassifier(num_clusters=50) # 减少聚类中心数量以加快处理速度bow_classifier.train(data_dir)except Exception as e:print(f"\n程序运行出错: {str(e)}")print("\n建议的解决方案:")print("1. 检查数据路径是否正确")print("2. 确保图像文件真实存在且可读")print("3. 尝试将数据复制到不含中文/特殊字符的路径")print("4. 检查图像文件是否损坏")finally:print("\n程序结束")
- 指定数据集所在的目录路径。
- 验证数据目录是否存在,并检查每个类别目录下的图像文件数量。
- 创建
BowClassifier
实例,并调用train
方法进行模型训练。 - 如果在运行过程中出现错误,打印错误信息并提供一些可能的解决方案。
三、运行结果与分析
(一)运行结果
运行程序后,程序会依次输出以下内容:
- 数据目录结构验证结果,显示每个类别目录下的图像文件数量。
- 特征提取过程中的进度信息,包括已处理的图像数量和跳过的图像数量。
- K-means 聚类过程的耗时和结果。
- SVM 分类器的训练耗时。
- 模型在测试集上的评估结果,包括分类报告、精确率、召回率和 F1 分数。
- 整个训练和评估过程的总耗时。
(二)结果分析
- 精确率(Precision):衡量模型预测为正类的样本中实际为正类的比例。较高的精确率表示模型的预测结果较为可靠。
- 召回率(Recall):衡量模型能够正确识别出的正类样本占所有正类样本的比例。较高的召回率表示模型能够较好地识别出正类样本。
- F1 分数:精确率和召回率的调和平均值,综合考虑了精确率和召回率的平衡。较高的 F1 分数表示模型在精确率和召回率之间取得了较好的平衡。
通过观察分类报告和评估指标,可以对模型的性能进行全面评估。如果模型的性能不理想,可以尝试以下方法进行优化:
- 调整聚类中心数量:增加或减少
num_clusters
的值,以改变视觉单词的数量,从而影响模型的特征表示能力。 - 改进特征提取方法:除了 SIFT 特征,还可以尝试使用其他特征提取算法,如 ORB、SURF 等。
- 调整 SVM 参数:通过调整 SVM 的核函数、惩罚参数等超参数,优化模型的分类性能。
- 增加数据量:扩充数据集,增加模型的训练样本数量,提高模型的泛化能力。
四、总结
本文介绍了基于词袋模型(BoW)和支持向量机(SVM)的猫狗图像分类方法,并提供了详细的代码实现。通过特征提取、聚类和分类的过程,实现了对猫狗图像的自动分类。实验结果表明,该方法能够取得较好的分类效果。在实际应用中,可以根据具体需求对模型进行优化和改进,以提高分类性能。希望本文的内容对读者有所帮助,能够为读者在图像分类领域的学习和研究提供一定的参考。
相关文章:
# 基于词袋模型(BoW)的猫狗图像分类实践
基于词袋模型(BoW)的猫狗图像分类实践 在计算机视觉领域,图像分类是一项基础且重要的任务。本文将介绍如何使用词袋模型(Bag of Words, BoW)结合支持向量机(SVM)实现猫狗图像分类。通过详细的代…...
Vscode+git笔记
1.U是untracked m是modify modified修改了的。 2.check out 查看观察 3 status changed 暂存区 4.fetch v 取来拿来 5.orangion 起源代表远程分支 git checkout就是可以理解为进入的意思。...
生成式 AI 的未来
在人类文明的长河中,技术革命始终是推动社会跃迁的核心引擎。从蒸汽机解放双手,到电力点亮黑夜,再到互联网编织全球神经网络,每一次技术浪潮都在重塑人类的生产方式与认知边界。而今天,生成式人工智能(Generative AI)正以一种前所未有的姿态登上历史舞台——它不再局限于…...
进程间通信(IPC)
进程间通信(IPC)是操作系统中非常重要且基础的概念,涉及到不同进程之间如何交换数据和同步操作。下面我会一个一个地详细讲解这几种常见的IPC方式:管道(包含匿名管道和有名管道)、消息队列、共享内存、信号量、Socket通信,内容尽量用通俗易懂的语言,并结合具体原理、优…...
C语言奇幻指南:宏、头文件与变量的秘密世界
🌟 C语言奇幻指南:宏、头文件与变量的秘密世界 🌟 一、写一个“比小”宏:三目运算符的魔法 目标:定义一个宏,返回两个参数中较小的值。 代码: #define MIN(a, b) ((a) < (b) ? (a) : (b))…...
【开源免费】二维码批量识别-未来之窗——C#-仙盟创梦IDE
二维码批量识别工具,借助先进图像识别技术,能快速准确读取大量二维码信息。适用于物流与供应链管理,如库存盘点和货物追踪;可用于资产管理,像固定资产盘点与设备巡检;还能助力数据收集与市场调研࿰…...
n8n工作流自动化平台的实操:解决中文乱码
解决问题: 通过ftp读取中文内容的文件,会存在乱码,如下图: 解决方案 1.详见《安装 iconv-lite》 2.在code节点,写如下代码: const iconv require(iconv-lite);const items $input.all(); items.forEa…...
MCP 探索:MCP 集成的相关网站 Smithery、PulseMCP 等
简简单单 Online zuozuo :本心、输入输出、结果 文章目录 MCP 探索:MCP 集成的相关网站 Smithery、PulseMCP 等前言一、MCP 集成基础二、利用热门资源平台集成三、集成常见 MCP 服务四、管理集成的 MCP 能力五、集成示例借鉴六、数据交互与安全管理MCP 探索:MCP 集成的相关网…...
linux的时间轮
时间轮:高效管理海量定时任务的利器 1. 引言:为什么需要时间轮? 在许多应用场景中,我们都需要管理大量的定时任务,例如: 网络连接的超时检测。分布式系统中的心跳检测。缓存条目的过期淘汰。需要延迟执行…...
《操作系统真象还原》第十二章(2)——进一步完善内核
文章目录 前言可变参数的原理实现系统调用write更新syscall.h更新syscall.c更新syscall-init.c 实现printf编写stdio.h编写stdio.c 第一次测试main.cmakefile结果截图 完善printf修改main.c 结语 前言 上部分链接:《操作系统真象还原》第十二章(1&#…...
MIT6.S081-lab8前置
MIT6.S081-lab8前置 注:本部分除了文件系统还包含了调度的内容。 调度 调度涉及到保存寄存器,恢复寄存器,就这一点而言,和我们的 trap 很像,但是实际上,我们实现并不是复用了 trap 的逻辑,我…...
Java从入门到精通 - Java语法
Java 语法 此笔记参考黑马教程,仅学习使用,如有侵权,联系必删 文章目录 Java 语法01 变量详解1. 变量里的数据在计算机中的存储原理1.1 二进制1.2 十进制转二进制的算法1.3 计算机中表示数据的最小单元总结1.4 字符在计算机中是如何存储的呢…...
【CF】Day50——Codeforces Round 960 (Div. 2) BCD
B. Array Craft 题目: 思路: 有点意思的构造 首先题目告诉我们 y < x,这是一个重要的条件 我们先来考虑简单情况,假如可以放0进去,那么我们只需要在 y ~ x 之间全放 1 ,其余都是 0 即可,但…...
MySQL 日期加减函数详解
MySQL 日期加减函数详解 1. DATE_ADD 函数 基本语法 DATE_ADD(date, INTERVAL expr unit)功能 在指定日期/时间上添加一个时间间隔 参数说明 date:要处理的日期/时间值(可以是DATE, DATETIME或TIMESTAMP类型)expr:要添加的间…...
NV189NV195美光固态闪存NV197NV199
NV189NV195美光固态闪存NV197NV199 在存储技术持续迭代的2025年,美光固态闪存NV189、NV195、NV197、NV199系列凭借其差异化的性能定位,正在重新定义数据存储的边界。本文将从技术参数、场景适配、行业价值等维度,为不同领域的专业人士提供深度…...
C语言-回调函数
回调函数 通过函数指针调用函数,而这个被调用的函数称为回调函数 回调函数是C语言中一种强大的机制,允许将函数作为参数传递给其他函数,从而在特定时机由后者调用。它的核心在于函数指针的使用 以下是回调函数的使用例子 先创建好一个函数…...
启发式算法-蚁群算法
蚁群算法是模拟蚂蚁觅食行为的仿生优化算法,原理是信息素的正反馈机制,蚂蚁通过释放信息素来引导同伴找到最短路径。把问题的元素抽象为多条路径,每次迭代时为每只蚂蚁构建一个解决方案,该解决方案对应一条完整的路径,…...
DeepSeek与MySQL:开启数据智能新时代
目录 一、引言:技术融合的力量二、DeepSeek 与 MySQL:技术基石2.1 DeepSeek 技术探秘2.2 MySQL 数据库深度解析 三、DeepSeek 与 MySQL 集成:从理论到实践3.1 集成原理剖析3.2 集成步骤详解 四、应用案例:实战中的价值体现4.1 电商…...
Modbus 通讯协议(超详细,简单易懂)
目录 一、协议中的寄存器定义 二、协议概述 三、使用串口的Modbus 报文帧 编辑 3.1、Modbus ASCII 模式 3.2、Modbus RTU 模式 3.3、功能码概要 3.4、Modbus 报文分析 四、什么是RS-485 RS-232? 一、协议中的寄存器定义 阅读 Modbus 协议时会发现它的概念别扭…...
单细胞测序试验设计赏析(一)
单细胞测序试验设计赏析(一) 单细胞测序试验设计中,单细胞测序技术通常会结合其它的技术来共同说明问题,或者结合年龄、性别等临床数据,进行分层分析说明问题以下以发表文章来进行一定的分析。 Single-cell RNA seque…...
ES6入门---第二单元 模块三:对象新增、
一:对象简洁语法: 1、变量简洁 <script>let name Strive;let age 18;let json {name, //name:name,age //age:age};console.log(json);</script> 2、函数简洁 let json {name, //name:name,age, //age:age/* showA:functi…...
多元随机变量协方差矩阵
主要记录多元随机变量数字特征相关内容。 关键词:多元统计分析 二元随机变量(X, Y) 说明:可以理解变量中的 X为身高、Y为体重 总体协方差 σ X Y c o v ( X , Y ) E [ ( X − μ X ) ( Y − μ Y ) ] E ( X Y ) − μ X μ Y \sigma_{XY}cov(X, Y)E[…...
计算机网络-同等学力计算机综合真题及答案
计算机网络-同等学力计算机综合真题及答案 (2003-2024) 2003 年网络 第二部分 计算机网络(共 30 分) (因大纲变动因此 2004 年真题仅附真题,不作解析。) 一、填空题(共 10 分&#…...
[案例二] 菜单条制作(Menuscript)与工具条制作(Toolbar)
最近五一正好毕业论文盲审,抽时间研究一下菜单条制作(Menuscript)与工具条制作(Toolbar)的制作,在NX二次开发中唐康林老师已经讲的很详细了,在这里只对视频中的内容进行总结,并且根据自己的想法进行补充。在里海博主的直播教学中发现一个很有趣的NX图标工具,本人大概做了一…...
bellard.org : QuickJS 如何使用 qjs 执行 js 脚本
参阅上一篇:Fabrice Bellard(个人网站:bellard.org)介绍 Fabrice Bellard(个人网站:bellard.org)是计算机领域最具影响力的程序员之一,其贡献跨越多个技术领域并持续推动开…...
计组复习笔记 3
前言 继续做例题。昨天做到第一个就把我难住了。可恶。 4.1 地址码越长,操作码越短。因为两者加起来是指令字,指令字的大小一般是固定的。扩展编码按照操作码从短到长进行编码。算了先放一下。我先看一下别的复习资料。等会儿再看这个题。 鼓励自己 …...
GCD 深入解析:从使用到底层实现
前言 Grand Central Dispatch (GCD) 是 Apple 基于 C 语言开发的一套完整的并发编程框架。它不仅仅是一个简单的线程管理工具,而是一个高度优化的并发编程解决方案。GCD 的设计理念是将并发编程的复杂性封装在框架内部,为开发者提供简单易用的接口。本文…...
JavaScript中的AES加密与解密:原理、代码与实战
前言 关于有js加密、js解密,js业务相关,找jsjiami官网站长v。 另外前段时间做了个单子跑单了,出售TEMU助手。eller点kuajingmaihuo点com的全自动化助手,可以批量合规,批量实拍图,批量资质上传等。 一、A…...
计算机组成原理实验(7) 堆指令部件模块实验
实验七 堆指令部件模块实验 一、实验目的 1、掌握指令部件的组成方式。 2、熟悉指令寄存器的打入操作,PC计数器的设置和加1操作,理解跳转指令的实现过程。 二、实验要求 按照实验步骤完成实验项目,掌握数据打入指令寄存器IR1、PC计数器的…...
Windows系统下Node.js环境部署指南:使用nvm管理多版本
Windows系统下Node.js环境部署指南:使用nvm管理多版本 一、Node.js介绍二、为什么需要nvm?三、安装前的准备工作1. 本次环境说明2. 卸载现有Node.js(如有) 三、nvm-windows安装步骤1. 下载安装包2. 安装过程3. 验证安装 四、使用n…...
数据结构*队列
队列 什么是队列 是一种线性的数据结构,和栈不同,队列遵循“先进先出”的原则。如下图所示: 在集合框架中我们可以看到LinkedList类继承了Queue类(队列)。 普通队列(Queue) Queue中的方法 …...
C语言蓝桥杯真题代码
以下是不同届蓝桥杯C语言真题代码示例,供参考: 第十三届蓝桥杯省赛 C语言大学B组 真题:卡片 题目:小蓝有很多数字卡片,每张卡片上都是数字1-9。他想拼出1到n的数列,每张卡片只能用一次,求最大的…...
Sharding-JDBC分库分表中的热点数据分布不均匀问题及解决方案
引言 在现代分布式应用中,使用Sharding-JDBC进行数据库的分库分表是提高系统性能和扩展性的常见策略。然而,在实际应用中,某些特定的数据(如最新订单、热门商品等)可能会成为“热点”,导致这些部分的数据处…...
Dagster中的Ops与Assets:数据管道构建的两种选择
Dagster是一个强大的数据编排平台,它提供了多种工具来帮助数据工程师构建可靠的数据管道。在Dagster中,Ops和Assets是两种核心概念,用于定义数据处理逻辑。本文将全面介绍Ops的概念、特性及其使用方法,特别补充了Op上下文和Op工厂…...
thonny提示自动补全功能
THONNY IDE 自动补全功能配置 在 Thonny IDE 中启用和优化自动补全功能可以显著提升编程体验。为了确保该功能正常工作,需要确认几个设置选项。 配置自动补全 Thonyy IDE 的自动补全默认情况下是开启的。如果发现自动补全未按预期运行,可以通过调整首选…...
PyTorch_阿达玛积
阿达玛积指的是矩阵对应位置的元素相乘,可以使用乘号运算符,也可以使用mul函数来完成计算。 代码 import torch import numpy as np # 1. 使用 mul 函数 def test01():data1 torch.tensor([[1, 2], [3, 4]])data2 torch.tensor([[5, 6], [7, 8]])dat…...
蓝桥杯 摆动序列
摆动序列 原题目链接 题目描述 如果一个序列的奇数项都比前一项大,偶数项都比前一项小,则称为一个摆动序列。 即对于任意整数 i(i ≥ 1)满足: a₂ᵢ < a₂ᵢ₋₁,a₂ᵢ₊₁ > a₂ᵢ 小明想知道&…...
AI 与生物技术的融合:开启精准医疗的新纪元
在科技飞速发展的今天,人工智能(AI)与生物技术的融合正在成为推动医疗领域变革的重要力量。精准医疗作为现代医学的重要发展方向,旨在通过深入了解个体的基因信息、生理特征和生活方式,为患者提供个性化的治疗方案。AI…...
三、shell脚本--运算符与表达式:让脚本学会“思考”
一、算术运算符:加减乘除取模 在我们写shell脚本时,做点基本的数学运算还是经常需要的。常用的算术运算符跟我们平时学的一样: : 加- : 减* : 乘 (小提示:有时候在某些命令里可能需要写成 \*)/ : 除 (在 Shell 里通常是取整数部分…...
c++ 指针参数传递的深层原理
指针参数传递的深层原理 理解为什么可以修改指针指向的内容但不能直接修改指针本身,需要深入理解指针在内存中的表示方式和函数参数传递机制。 1. 指针的内存表示 指针本质上是一个变量,它存储的是另一个变量的内存地址。在内存中: 假设有…...
【查看.ipynp 文件】
目录 如何打开 .ipynb 文件? 如果确实是 .ipynp 文件: .ipynp 并不是常见的 Jupyter Notebook 文件格式。通常,Jupyter Notebook 文件的扩展名是 .ipynb(即 Interactive Python Notebook)。如果你遇到的是 .ipynb 文…...
C++ 简单工厂模式详解
简单工厂模式(Simple Factory Pattern)是最简单的工厂模式,它不属于GoF 23种设计模式,但它是工厂方法模式和抽象工厂模式的基础。 概念解析 简单工厂模式的核心思想是: 将对象的创建逻辑集中在一个工厂类中 客户端不…...
ubuntu使用apt安装软件
1、使用apt list |grep jdk查看要安装的软件 此处以jdk为例 2、执行名称:安装指定版本的软件 sudo apt install openjdk-11-jdk...
TFT(薄膜晶体管)和LCD(液晶显示器)区别
TFT(薄膜晶体管)和LCD(液晶显示器)是显示技术中常见的术语,二者既有联系又有区别。以下是它们的核心区别和关系: 1. 基本概念 LCD(液晶显示器) LCD是一种利用液晶材料特性控制光线通…...
【文献阅读】中国湿地随着保护和修复的反弹
一、研究背景 滨海湿地是全球最具生态价值的生态系统之一,广泛分布在河口、潮间带、泻湖和盐沼等地带,在调节气候、水质净化、生物栖息以及防止海岸侵蚀等方面发挥着关键作用。然而,近年来滨海湿地正面临严峻威胁,全球估计约有50%…...
用Ensaio下载GIS数据
文章目录 简介重力场绘制 简介 Ensaio在葡萄牙语中是随笔的意思,是一个用于下载开源数据集的python库。其底层基于Pooch来下载和管理数据。 Ensaio可通过pip或者conda来安装 pip isntall ensaio conda install ensaio --channel conda-forge由于这个库功能较为单…...
【算法基础】递归算法 - JAVA
一、递归基础 1.1 什么是递归算法 递归算法是一种通过函数调用自身来解决问题的方法。简单来说,就是"自己调用自己"。递归将复杂问题分解为同类的更简单子问题,直到达到易于直接解决的基本情况。 1.2 递归的核心要素 递归算法由两个关键部…...
连续变量与离散变量的互信息法
1. 互信息法简介 互信息(Mutual Information, MI) 是一种衡量两个变量之间相互依赖程度的统计量,它来源于信息论。互信息可以用于评估特征与目标变量之间的相关性,无论这些变量是连续的还是离散的。互信息法是一种强大的特征选择…...
java_Lambda表达式
1、背景 lambda表达式是Java SE 8中一个重要的新特性。lambda表达式允许你通过表达式来代替功能接口。lambda表达式就和方法一样样,它提供了一个正常的参数列表和一个使用这些参数的主体(body,可以是一个表达式和一个代码块)。La…...
Python Cookbook-6.17 NuIl对象设计模式的实现
任务 你想减少代码中的条件声明,尤其是针对特殊情况的检查。 解决方案 一种常见的代表“这里什么也没有”的占位符是 None,但我们还可以定义一个类,其行为方式和这种占位符相似,而且效果更好: class Null(object):Null对象总是…...