深入理解 Pandas 核心数据结构:Series 与 DataFrame
Series:一维标签化数组
Series 是 Pandas 中的基本构建模块之一,可以看作是一种带有索引的一维数组。它由两部分组成:实际的数据值(Values)和与之相关的标签(Index)。Series 可以存储任何数据类型,但在实际应用中,通常为了性能和逻辑清晰,会保持内部数据类型的一致性。
1. 创建 Series 对象
在 Pandas 中,可以通过 pandas.Series(data, index, dtype, name) 来构建对象。支持多种数据源输入:
使用列表或 Numpy 数组
import pandas as pd
import numpy as np
# 使用列表创建,未指定索引时默认从 0 开始
data_list = [10, 25.5, 'Pandas', [1, 2]]
s1 = pd.Series(data_list)
print(s1)
使用字典创建
字典的键(Key)会自动转换为 Series 的索引,值(Value)对应数据内容。
# 字典创建,并可以通过 index 参数过滤或重新排序
price_map = {'Apple': 15, 'Banana': 8, 'Cherry': 20}
s2 = pd.Series(price_map, index=['Cherry', 'Apple', 'Orange'])
# Orange 在原字典中不存在,将显示为 NaN
print(s2)
使用标量创建
如果数据是单一标量,则必须提供索引,Series 会根据索引长度重复该标量。
s3 = pd.Series(99, index=['r1', 'r2', 'r3'])
print(s3)
2. 访问与索引
Series 提供了显式标签索引和隐式位置索引两种方式。
- 显式索引 (loc): 使用自定义的标签进行检索。
- 隐式索引 (iloc): 使用类似于 Python 列表的 0 到 N-1 的整数下标。
# 索引示例
demo_s = pd.Series([100, 200, 300], index=['a', 'b', 'c'])
print(demo_s['a']) # 显式访问
print(demo_s.iloc[0]) # 隐式访问
# 切片操作
print(demo_s['a':'b']) # 标签切片:包含末端
print(demo_s[0:2]) # 位置切片:左闭右开
3. 数据运算与对齐
Series 运算的一个核心特征是自动索引对齐。当两个 Series 进行运算时,Pandas 会根据索引标签进行匹配。如果某个标签只存在于其中一个对象中,结果将填充为 NaN。
s_v1 = pd.Series([1, 2], index=['x', 'y'])
s_v2 = pd.Series([3, 4], index=['y', 'z'])
# 结果中 x 和 z 索引的值将是 NaN
print(s_v1 + s_v2)
DataFrame:二维表格化数据结构
DataFrame 是一个表格型的数据结构,包含有序的列集合,每一列可以是不同的值类型。它可以被视为由多个共用相同索引的 Series 组成的集合。
1. DataFrame 的创建方式
DataFrame 的创建非常灵活,以下是几种常用的方法:
通过字典(键为列名,值为列表)
inventory_data = {
'Product': ['Laptop', 'Mouse', 'Monitor'],
'Stock': [15, 50, 20],
'Price': [5000, 150, 1200]
}
df_inv = pd.DataFrame(inventory_data)
print(df_inv)
通过列表嵌套字典
每一个字典代表一行数据,键是列名。
row_data = [
{'Name': 'Alice', 'Dept': 'HR'},
{'Name': 'Bob', 'Dept': 'IT', 'Salary': 5000}
]
df_emp = pd.DataFrame(row_data)
print(df_emp) # 缺失字段自动补 NaN
2. 数据筛选与定位
在 DataFrame 中,可以通过多种方式提取子集:
- 选取列:
df['ColumnName']或df.ColumnName。 - 选取行: 建议使用
loc(标签) 或iloc(位置)。
# 选取 'Product' 和 'Price' 两列
print(df_inv[['Product', 'Price']])
# 选取第一行数据
print(df_inv.iloc[0])
# 选取特定行和列
print(df_inv.loc[0:1, ['Product', 'Stock']])
3. 常用操作:增删改查
列的添加与删除
# 添加新列
df_inv['Total_Value'] = df_inv['Stock'] * df_inv['Price']
# 删除列(drop 不修改原对象,除非指定 inplace=True)
df_reduced = df_inv.drop('Price', axis=1)
# 使用 del 直接从原对象删除
del df_inv['Stock']
4. 数据合并 (Merge)
merge 方法类似于 SQL 中的 Join 操作,可以根据一个或多个键将不同 DataFrame 的行连接起来。
left_df = pd.DataFrame({'ID': [1, 2, 3], 'Info': ['A', 'B', 'C']})
right_df = pd.DataFrame({'ID': [2, 3, 4], 'Score': [85, 90, 77]})
# 内连接:只保留键值共同存在的部分
merged_inner = pd.merge(left_df, right_df, on='ID', how='inner')
print(merged_inner)
# 左连接:保留左表所有行
merged_left = pd.merge(left_df, right_df, on='ID', how='left')
print(merged_left)