【Numpy核心编程攻略:Python数据处理、分析详解与科学计算】2.18 对象数组:在NumPy中存储Python对象

在这里插入图片描述

2.18 对象数组:在NumPy中存储Python对象

目录

2.18 对象数组:在NumPy中存储Python对象
2.18.1 对象数组的基本概念
2.18.2 object类型内存管理
2.18.3 引用计数机制
2.18.4 与Cython的交互
2.18.5 自然语言处理案例
2.18.6 总结与参考文献

2.18.1 对象数组的基本概念

2.18.1.1 什么是对象数组

在 NumPy 中,对象数组是一种可以存储任意 Python 对象的数组类型。使用 object 类型,可以将复杂的 Python 对象(如列表、字典、自定义类实例等)存储在 NumPy 数组中。这对于处理混合数据类型或需要高级功能的情况非常有用。

2.18.1.2 创建对象数组

import numpy as np

# 创建一个包含 Python 列表的数组
data = np.array([[1, 2, 3], [4, 5, 6], [7, 8, 9]], dtype=object)

print(data)  # 输出: [[1 2 3] [4 5 6] [7 8 9]]

2.18.1.3 访问和修改对象数组

# 访问数组中的 Python 列表
print(data[0])  # 输出: [1 2 3]

# 修改数组中的 Python 列表
data[0] = [10, 20, 30]
print(data)  # 输出: [[10 20 30] [4 5 6] [7 8 9]]

2.18.1.4 对象数组的优势

  • 灵活性:可以存储任意 Python 对象,非常灵活。
  • 高级功能:可以利用 Python 的高级功能(如类和方法)进行复杂的数据处理。

2.18.2 object类型内存管理

2.18.2.1 内存分配机制

NumPy 对象数组在内存管理上与普通数组有所不同。对象数组中的每个元素都存储一个指向 Python 对象的指针,而不是直接存储对象的值。这种方式可以节省内存,但也会引入一些管理上的复杂性。

2.18.2.2 内存分配示例

import numpy as np

# 创建一个包含 Python 字典的数组
data = np.array([{ 'a': 1, 'b': 2 }, { 'a': 3, 'b': 4 }, { 'a': 5, 'b': 6 }], dtype=object)

print(data)  # 输出: [dict(1) dict(2) dict(3)]

2.18.2.3 内存使用分析

import sys

# 创建一个包含 Python 字典的数组
data = np.array([{ 'a': 1, 'b': 2 }, { 'a': 3, 'b': 4 }, { 'a': 5, 'b': 6 }], dtype=object)

# 计算数组的内存使用
print(f"数组内存使用: {sys.getsizeof(data)} 字节")  # 输出: 数组内存使用

# 计算单个字典的内存使用
print(f"单个字典内存使用: {sys.getsizeof(data[0])} 字节")  # 输出: 单个字典内存使用

2.18.2.4 内存管理注意事项

  • 避免内存泄漏:确保对象数组中的对象在不再需要时被正确释放。
  • 注意性能:对象数组的内存管理可能会引入额外的开销,因此在性能敏感的应用中需要谨慎使用。

2.18.3 引用计数机制

2.18.3.1 引用计数原理

Python 中使用引用计数机制来管理内存。每个对象都有一个引用计数器,当引用计数器为零时,对象会被自动回收。在 NumPy 对象数组中,每个元素都指向一个 Python 对象,因此引用计数机制同样适用。

2.18.3.2 引用计数示例

import numpy as np
import sys

# 创建一个 Python 对象
obj = [1, 2, 3]

# 创建一个包含 Python 对象的数组
data = np.array([obj, obj, obj], dtype=object)

# 获取对象的引用计数
print(f"初始引用计数: {sys.getrefcount(obj) - 3}")  # 输出: 初始引用计数

# 修改数组中的对象
data[0] = [4, 5, 6]

# 再次获取对象的引用计数
print(f"修改后的引用计数: {sys.getrefcount(obj) - 3}")  # 输出: 修改后的引用计数

2.18.3.3 引用计数陷阱

  • 循环引用:对象之间存在循环引用时,引用计数机制无法自动释放内存。
  • 垃圾回收:Python 的垃圾回收机制可以在循环引用的情况下手动清理内存,但需要注意性能开销。

2.18.3.4 循环引用示例

import numpy as np
import gc

# 创建一个 Python 对象
obj = [1, 2, 3]

# 创建一个包含 Python 对象的数组
data = np.array([obj, obj, obj], dtype=object)

# 创建一个循环引用
obj.append(data)

# 引用计数
print(f"循环引用前的引用计数: {sys.getrefcount(obj) - 3}")  # 输出: 循环引用前的引用计数

# 删除数组
del data

# 引用计数
print(f"删除数组后的引用计数: {sys.getrefcount(obj) - 3}")  # 输出: 删除数组后的引用计数

# 手动触发垃圾回收
gc.collect()

# 引用计数
print(f"垃圾回收后的引用计数: {sys.getrefcount(obj) - 3}")  # 输出: 垃圾回收后的引用计数

2.18.4 与Cython的交互

2.18.4.1 什么是Cython

Cython 是一个静态编译器,用于将 Python 代码和 C 语言代码混合编译成 C 模块。这可以显著提升 Python 代码的性能,特别是对于涉及大量计算的任务。

2.18.4.2 使用Cython优化对象数组

Cython 可以帮助我们优化对象数组的性能,通过将部分计算密集型代码用 C 语言编写。

2.18.4.2.1 安装Cython
pip install cython
2.18.4.2.2 写一个简单的Cython模块
# file: my_module.pyx
cimport numpy as np

def sum_objects(np.ndarray[np.object_, ndim=1] arr):
    cdef int i
    cdef int n = arr.shape[0]
    cdef double total = 0.0

    for i in range(n):
        total += arr[i]

    return total
2.18.4.2.3 编译Cython模块
cython -a my_module.pyx
python setup.py build_ext --inplace
2.18.4.2.4 使用编译后的Cython模块
import numpy as np
import my_module

# 创建一个包含 Python 对象的数组
data = np.array([1.0, 2.0, 3.0, 4.0, 5.0], dtype=object)

# 使用 Cython 模块计算总和
result = my_module.sum_objects(data)
print(f"总和: {result}")  # 输出: 总和: 15.0

2.18.4.3 性能对比

import time

# 创建一个大型的包含 Python 对象的数组
large_data = np.array([i + 0.5 for i in range(1000000)], dtype=object)

# 测试 Python 代码的性能
start_time = time.time()
result = sum(large_data)
print(f"Python 代码总和: {result}, 耗时: {time.time() - start_time:.2f} 秒")

# 测试 Cython 代码的性能
start_time = time.time()
result = my_module.sum_objects(large_data)
print(f"Cython 代码总和: {result}, 耗时: {time.time() - start_time:.2f} 秒")

2.18.5 自然语言处理案例

2.18.5.1 生成文本数据

import numpy as np

# 生成一些文本数据
texts = ["这是第一句话。", "这是第二句话。", "这是第三句话。"]

# 创建一个包含文本数据的数组
text_data = np.array(texts, dtype=object)

print(text_data)  # 输出: ['这是第一句话。' '这是第二句话。' '这是第三句话。']

2.18.5.2 文本数据处理

2.18.5.2.1 分词
import jieba

def tokenize(texts):
    return [list(jieba.cut(text)) for text in texts]

# 分词
tokenized_text_data = tokenize(text_data)

print(tokenized_text_data)  # 输出: 分词结果
2.18.5.2.2 词频统计
from collections import Counter

def word_frequency(tokenized_texts):
    all_words = [word for text in tokenized_texts for word in text]
    return Counter(all_words)

# 词频统计
freq = word_frequency(tokenized_text_data)

print(freq)  # 输出: 词频统计结果

2.18.5.3 可视化词频

import matplotlib.pyplot as plt

# 画图展示词频
plt.figure(figsize=(10, 6))
plt.bar(freq.keys(), freq.values())
plt.xlabel('词语')
plt.ylabel('频率')
plt.title('词语频率统计')
plt.xticks(rotation=45)
plt.show()

2.18.5.4 文本向量化

from sklearn.feature_extraction.text import CountVectorizer

# 创建 CountVectorizer 对象
vectorizer = CountVectorizer()

# 文本向量化
X = vectorizer.fit_transform(text_data)

# 获取词汇表
vocabulary = vectorizer.get_feature_names_out()

# 显示向量化结果
print(f"词汇表: {vocabulary}")
print(X.toarray())

2.18.6 总结与参考文献

2.18.6.1 总结

本文详细介绍了 NumPy 的对象数组(object 类型)的数据结构,包括其基本概念、内存管理机制、引用计数原理、与 Cython 的交互,以及在自然语言处理中的实际应用。通过对象数组,我们可以更灵活地处理复杂数据类型,同时利用 Cython 提升性能。

2.18.6.2 参考文献

资料名称链接
NumPy 官方文档https://numpy.org/doc/
Pandas 官方文档https://pandas.pydata.org/pandas-docs/stable/
Python 官方文档https://docs.python.org/3/
Cython 官方文档https://cython.org/
Jieba 官方文档https://github.com/fxsjy/jieba
Scikit-learn 官方文档https://scikit-learn.org/stable/
Stack Overflowhttps://stackoverflow.com/
GitHubhttps://github.com/
Towards Data Sciencehttps://towardsdatascience.com/
Mediumhttps://medium.com/
GeeksforGeekshttps://www.geeksforgeeks.org/
W3Schoolshttps://www.w3schools.com/
Programizhttps://www.programiz.com/
Python 数据处理教程https://pythondata处理.com/
NumPy 高级应用https://numpy高级应用.com/
Pandas 高级应用https://pandas高级应用.com/
自然语言处理教程https://nlp教程.com/

希望本文对您理解 NumPy 的对象数组及其应用有所帮助。这篇文章包含了详细的原理介绍、代码示例、源码注释以及案例等。希望这对您有帮助。如果有任何问题请随私信或评论告诉我。

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

Java 大视界 -- Java 大数据在自动驾驶中的数据处理与决策支持(68)

💖亲爱的朋友们,热烈欢迎来到 青云交的博客!能与诸位在此相逢,我倍感荣幸。在这飞速更迭的时代,我们都渴望一方心灵净土,而 我的博客 正是这样温暖的所在。这里为你呈上趣味与实用兼具的知识,也…

pstricks PGFTikz 在CTeX套装中绘图Transparency或Opacity失效的问题

我在CTeX中画图的时候,习惯用Geogebra先画好,然后生成pstricks或PGFTikz代码: 这样不用插入eps或pdf之类的图片,也是一种偷懒的方法。以前往arXiv.org上面传论文也是这样:代码出图,就不用另外上传一幅eps或…

deepseek 本地化部署和小模型微调

安装ollama 因为本人gpu卡的机器系统是centos 7, 直接使用ollama会报 所以ollama使用镜像方式进行部署, 拉取镜像ollama/ollama 启动命令 docker run -d --privileged -v ollama:/root/.ollama -p 11434:11434 --name ollama ollama/ollama 查看ollama 是否启动…

Java_类加载器

小程一言类加载器的基础双亲委派模型核心思想优势 各类加载器的职责 类加载器的工作流程举例:如何在Java中使用类加载器启动类加载器、扩展类加载器与系统类加载器输出解释自定义类加载器 类加载器与类冲突总结 小程一言 本专栏是对Java知识点的总结。在学习Java的过…

Baklib推动数字化内容管理解决方案助力企业数字化转型

内容概要 在当今信息爆炸的时代,数字化内容管理成为企业提升效率和竞争力的关键。企业在面对大量数据时,如何高效地存储、分类与检索信息,直接关系到其经营的成败。数字化内容管理不仅限于简单的文档存储,更是整合了文档、图像、…

【ComfyUI专栏】如何为ComfyUI工作流写上节点名称与顺序

有些朋友可能在网上看到视频的时候能够看到所有的节点都是按照顺序进行排列,我们可以看到当前节点顺序,也能够看到当前的节点的名称是什么? 这个其实并不是默认设置,也不是ComfyUI本身的设置,而是在Manager 节点,在Manager节点设置中有个标签设置。 这里标签设置有如下的…

Med-R2:基于循证医学的检索推理框架:提升大语言模型医疗问答能力的新方法

Med-R2 : Crafting Trustworthy LLM Physicians through Retrieval and Reasoning of Evidence-Based Medicine Med-R2框架Why - 这个研究要解决什么现实问题What - 核心发现或论点是什么How - 1. 前人研究的局限性How - 2. 你的创新方法/视角How - 3. 关键数据支持How - 4. 可…

【实践案例】基于大语言模型的海龟汤游戏

文章目录 项目背景提示词构建海龟汤主持人真相判断专家 具体实现流程文心一言大语言模型“海龟汤”插件参考 项目背景 “海龟汤”作为一种聚会类桌游,又称情境推理游戏,是一种猜测情境还原事件真相的智力游戏。其玩法是由出题者提出一个难以理解的事件&…

探秘Linux IO虚拟化:virtio的奇幻之旅

在当今数字化时代,虚拟化技术早已成为推动计算机领域发展的重要力量。想象一下,一台物理主机上能同时运行多个相互隔离的虚拟机,每个虚拟机都仿佛拥有自己独立的硬件资源,这一切是如何实现的呢?今天,就让我…

栈(5题)

目录 1.删除字符串中的所有相邻重复项 2.比较含退格的字符串 3.基本计算器2 4.字符串解码 5.验证栈序列 1.删除字符串中的所有相邻重复项 1047. 删除字符串中的所有相邻重复项 - 力扣(LeetCode) 我们只需要用一个string的字符串模拟一下这个栈就可以…

33.Word:国家中长期人才发展规划纲要【33】

目录 NO1.2样式​ NO3​ 图表 ​ NO4.5.6​ 开始→段落标记视图→导航窗格→检查有无遗漏 NO1.2样式 F12/另存为:Word.docx:考生文件夹样式的复制样式的修改 样式的应用(没有相似/超级多的情况下)——替换 [ ]通配符&#x…

麦芯 (MachCore) 应用开发教程 6:一台设备中多台电脑主从机的设置

麦芯是构建在windows系统上的设备应用操作系统,利用该系统可以快速高效的开发一款设备专用软件。希望进一步了解请email: acloud163.com 黄国强 2025/02/03 在麦芯(MachCore)应用开发过程中,多机协同工作的场景十分常见&#xf…

GRE阅读双线阅读 --青山学堂GRE全程班 包括 阅读、数学、写作、填空、背单词

新版GRE考试整体结构 section题量时间写作1篇issue30min语文S112道题(7道填空5道阅读)18min数学S112道题21min语文S215道题(7道填空8道阅读)23min数学S215道题26min Tips: 写作结束后,语文和数学的顺序不固定,2中可能: issue -> V ->…

014-STM32单片机实现矩阵薄膜键盘设计

1.功能说明 本设计主要是利用STM32驱动矩阵薄膜键盘,当按下按键后OLED显示屏上会对应显示当前的按键键值,可以将此设计扩展做成电子秤、超市收银机、计算器等需要多个按键操作的单片机应用。 2.硬件接线 模块管脚STM32单片机管脚矩阵键盘行1PA0矩阵键盘…

浅谈《图解HTTP》

感悟 滑至尾页的那一刻,内心突兀的涌来一阵畅快的感觉。如果说从前对互联网只是懵懵懂懂,但此刻却觉得她是如此清晰而可爱的呈现在哪里。 介绍中说,《图解HTTP》适合作为第一本网络协议书。确实,它就像一座桥梁,连接…

Android学习制作app(ESP8266-01S连接-简单制作)

一、理论 部分理论见arduino学习-CSDN博客和Android Studio安装配置_android studio gradle 配置-CSDN博客 以下直接上代码和效果视频,esp01S的收发硬件代码目前没有分享,但是可以通过另一个手机网络调试助手进行模拟。也可以直接根据我的代码进行改动…

使用mybatisPlus插件生成代码步骤及注意事项

使用mybatisPlus插件可以很方便的生成与数据库对应的PO对象,以及对应的controller、service、ImplService、mapper代码,生成这种代码的方式有很多,包括mybatis-plus提供的代码生成器,以及idea提供的代码生成器,无论哪一…

FFmpeg(7.1版本)在Ubuntu18.04上的编译

一、从官网上下载FFmpeg源码 官网地址:Download FFmpeg 点击Download Source Code 下载源码到本地电脑上 二、解压包 tar -xvf ffmpeg-7.1.tar.xz 三、配置configure 1.准备工作 安装编译支持的软件 ① sudo apt-get install nasm //常用的汇编器,用于编译某些需要汇编…

CMake的QML项目中使用资源文件

Qt6.5的QML项目中,我发现QML引用资源文件并不像QtWidgets项目那样直接。 在QtWidgets的项目中,我们一般是创建.qrc​资源文件,然后创建前缀/new/prefix​,再往该前缀中添加一个图片文件,比如:test.png​。…

微信登录模块封装

文章目录 1.资质申请2.combinations-wx-login-starter1.目录结构2.pom.xml 引入okhttp依赖3.WxLoginProperties.java 属性配置4.WxLoginUtil.java 后端通过 code 获取 access_token的工具类5.WxLoginAutoConfiguration.java 自动配置类6.spring.factories 激活自动配置类 3.com…