PyTorch 基础:数据操作与数据预处理

数据操作与数据预处理

本文整理自李沐老师《动手学深度学习》课程笔记,涵盖张量的基本操作与 Pandas 数据预处理流程,是深度学习入门的必备基础。


一、数据操作:张量基础

1. 创建张量

python 复制代码
import torch

x = torch.arange(12)        # 创建 0~11 的一维张量
x.shape                     # 查看形状:torch.Size([12])
x.numel()                   # 查看标量总个数:12

x = x.reshape(3, 4)         # 变形为 3×4 矩阵
                            # reshape 返回的是 view(视图),与原张量共享内存

torch.zeros((2, 3, 4))      # 全零张量
torch.ones((2, 3, 4))       # 全一张量
torch.tensor([[1, 2], [3, 4]])  # 由 Python 列表创建张量

2. 基本运算

python 复制代码
x = torch.tensor([1.0, 2, 4, 8])
y = torch.tensor([2, 2, 2, 2])

x + y   # 加
x - y   # 减
x * y   # 乘
x / y   # 除
x ** y  # 幂运算(** 是求幂运算符)

3. 张量拼接

python 复制代码
x = torch.arange(12, dtype=torch.float32).reshape(3, 4)
y = torch.tensor([[1, 2, 3, 4],
                  [1, 2, 3, 4],
                  [1, 2, 3, 4]])

torch.cat((x, y), dim=0)  # 沿行方向拼接,结果形状 (6, 4)
torch.cat((x, y), dim=1)  # 沿列方向拼接,结果形状 (3, 8)

4. 逻辑判断与求和

python 复制代码
x == y    # 逐元素比较,返回布尔张量
x.sum()   # 对所有元素求和,返回标量张量

5. 广播机制

不同形状的张量相加时,PyTorch 会自动触发广播(Broadcasting):

python 复制代码
x = torch.arange(3).reshape(3, 1)  # 形状 (3, 1)
y = torch.arange(2).reshape(1, 2)  # 形状 (1, 2)

x + y  # 广播后结果形状为 (3, 2)

6. 索引与切片

python 复制代码
x[-1]     # 最后一行
x[1:3]    # 第 1~2 行(左闭右开)
x[1, 0] = 9  # 修改指定位置的值

7. 内存管理:原地操作

python 复制代码
before = id(y)
y = y + x          # 为新结果分配了新内存
id(y) == before    # False,y 指向了新地址

# 原地操作:避免重复分配内存
z = torch.zeros_like(y)
print(id(z))
z[:] = x + y       # 原地写入,z 的地址不变
print(id(z))       # 与上面相同

为什么要在意内存?

在大规模模型训练中,反复执行 x = x + y 会不断申请新内存,极易导致内存溢出。

使用 x[:] = x + yx += y 可以做到原地更新,显著降低内存开销。

8. 与 NumPy 互转

python 复制代码
a = x.numpy()           # Tensor → NumPy ndarray
b = torch.tensor(a)     # NumPy ndarray → Tensor
type(a), type(b)

9. 单元素张量转 Python 标量

python 复制代码
a = torch.tensor([3.5])
a.item()   # 转为 Python float
float(a)   # 同上
int(a)     # 转为 Python int

二、数据预处理:从 CSV 到张量

真实场景中,数据往往以表格形式存储,需要经过读取、清洗、编码等步骤后才能喂给模型。

1. 创建示例数据集

python 复制代码
import os
import pandas as pd
import torch

os.makedirs(os.path.join('.', 'data'), exist_ok=True)
data_file = os.path.join('.', 'data', 'house_tiny.csv')

with open(data_file, 'w') as f:
    f.write('NumRooms,Alley,Price\n')
    f.write('NA,Pave,127500\n')
    f.write('2,NA,106000\n')
    f.write('4,NA,178100\n')
    f.write('NA,NA,140000\n')

2. 读取与分割数据

python 复制代码
data = pd.read_csv(data_file)
print(data)

inputs, outputs = data.iloc[:, 0:2], data.iloc[:, 2]

3. 缺失值处理

python 复制代码
# 注意:直接 fillna(mean()) 会因非数值列报错
# 正确做法:只对数值列做均值填充

numeric_cols = inputs.select_dtypes(include='number').columns
inputs[numeric_cols] = inputs[numeric_cols].fillna(inputs[numeric_cols].mean())
print(inputs)

4. 类别特征独热编码

python 复制代码
# get_dummies 将字符串列转为 0/1 编码,dummy_na=True 会为 NaN 单独生成一列
inputs = pd.get_dummies(inputs, dummy_na=True, dtype=int)
print(inputs)

5. 转换为张量

python 复制代码
X = torch.tensor(inputs.values)
y = torch.tensor(outputs.values)
# 注意:Pandas 默认转为 float64,但深度学习中通常使用 float32
# 如有需要,可指定:torch.tensor(inputs.values, dtype=torch.float32)
X, y

三、小结

知识点 核心要点
reshape 返回 view,与原张量共享内存
广播机制 形状不同的张量运算时自动扩展维度
原地操作 x += y / x[:] = ... 避免内存浪费
缺失值处理 数值列均值填充,类别列独热编码
张量类型 深度学习中优先使用 float32
相关推荐
七颗糖很甜1 小时前
开源雷达NEXRAD Level 3 数据完整获取与 Python 处理教程
大数据·python·算法
刘大猫.2 小时前
谷歌或将推出无屏健身手环 Fitbit Air,主打 AI 数字化健康教练
人工智能·ai·大模型·谷歌·算力·无屏健身手环·fitbit air
格林威2 小时前
面阵相机 vs 线阵相机:堡盟与海康相机选型差异全解析 附C# 实战演示
开发语言·人工智能·数码相机·计算机视觉·c#·视觉检测·工业相机
ydmy2 小时前
Embedding层(个人理解)
python·深度学习·embedding
cui17875682 小时前
排队免单模式:从爆火到优化,探寻实体商业新出路
大数据·人工智能·设计模式·个人开发·设计规范
qq_330037992 小时前
mysql在高并发下如何优化索引更新_mysql锁策略与调整
jvm·数据库·python
波动几何2 小时前
第三代人工智能:因果仿真范式
人工智能
财迅通Ai2 小时前
九丰能源2025年年报:主业稳健提质,新兴业务开辟增长新极
人工智能·能源·九丰能源
FrontAI2 小时前
深入浅出 LangGraph —— 第5章:条件边与动态路由
人工智能·langchain·ai agent·langgraph