【AI学习——Pandas入门】沉浸式速通Pandas
1. 核心数据结构:掌握Series(一维带标签数组)与DataFrame(二维表格数据)的定义、特点及关联,是学习Pandas的基础。2. 数据读取:理解read_csv()/read_excel()的核心参数逻辑,明确“参数匹配数据格式”和“读取后验证”的重要性。3. 数据清洗:掌握缺失值、重复值、异常值的“识别-处理”核心思路,牢记“最小干预”原则,根据数据情况选择合适处理方式。
目录
1. 分组统计核心逻辑(Split-Apply-Combine)
学习目标:
掌握Pandas基础核心知识,结合简单实操代码理解核心数据结构、数据读取、数据清洗及分组统计的用法,适合Pandas初学者入门;本文代码聚焦基础用法,避免复杂逻辑,帮助快速建立理论与实操的关联。
前置认知:
Pandas是Python生态中用于数据处理与分析的核心库,专为结构化数据设计,能高效完成数据的读取、清洗、转换、统计等操作,是AI/数据分析学习的必备基础工具。
一、Pandas核心基础:核心数据结构
Pandas的所有操作都基于两种核心数据结构,理解它们是掌握Pandas的前提,初学者需重点区分两者的定义、特点与适用场景。
1. Series:一维带标签数组
Series是由一组数据(可以是任意数据类型:整数、字符串、浮点数等)和一组与之对应的标签(索引,index)组成的一维数据结构,可理解为“带索引的数组”。
示例代码:
import pandas as pd
# 默认索引(0、1、2...)的Series
s1 = pd.Series([18, 20, 2.2, 19])
# 自定义索引的Series(索引为姓名)
s2 = pd.Series([85, 92, 78, 90], index=["张三", "李四", "王五", "赵六"])
print(s1)
print(s2)
print(s2.shape)
print(s2.index)
print(s2.values)
运行结果:
0 18.0
1 20.0
2 2.2
3 19.0
dtype: float64
张三 85
李四 92
王五 78
赵六 90
dtype: int64
s2的数据长度: (4,)
s2的索引: Index(['张三', '李四', '王五', '赵六'], dtype='object')
s2的数据值: [85 92 78 90]
核心特点:
索引唯一:索引是Series的核心标识,用于数据定位。
数据类型灵活:单个Series可容纳一种数据类型,不同Series的数据类型可不同。
自带属性:拥有dtype(数据类型)、shape(数据长度)、index(索引)、values(数据值)等属性,可快速获取数据基本信息。
适用场景:存储单一维度的数据,如某班级所有学生的年龄、某商品的月度销量等。
2. DataFrame:二维表格型数据结构
DataFrame是由多个Series按列组合而成的二维数据结构,包含行索引(index)和列索引(columns),可理解为“带索引的Excel表格”,是Pandas中最常用的数据结构。
示例代码:
import pandas as pd
# 用字典创建DataFrame(键为列名,值为对应列的Series数据)
data = {
"姓名": ["张三", "李四", "王五", "赵六"],
"年龄": [18, 20, 22, 19],
"成绩": [85, 92, 78, 90]
}
df = pd.DataFrame(data)
print(df)
# 从DataFrame中提取某一列(即Series)
age_series = df["年龄"]
print(age_series)
运行结果:
姓名 年龄 成绩
0 张三 18 85
1 李四 20 92
2 王五 22 78
3 赵六 19 90
0 18
1 20
2 22
3 19
Name: 年龄, dtype: int64
核心特点:
二维结构:既有行索引也有列索引,行索引标识行数据,列索引标识列数据(即对应的Series)。
列类型可多样:不同列(Series)的数据类型可不同(如一列是字符串、一列是整数、一列是浮点数)。
可灵活扩展:支持新增/删除行、列,也可修改索引和列名,适配数据处理过程中的各种需求。
集成Series特性:每一列都是一个Series,可通过列名快速提取对应列的数据进行单独处理。
适用场景:存储结构化数据,如学生信息表(含姓名、年龄、成绩等列)、商品数据表(含名称、价格、销量等列),是后续数据处理、统计的主要载体。
3. Series与DataFrame常用基础操作
(1)Series常用操作
核心聚焦索引定位、数据筛选和简单计算,代码示例如下:
# 延续前文创建的s2(姓名为索引,成绩为数据)
import pandas as pd
s2 = pd.Series([85, 92, 78, 90], index=["张三", "李四", "王五", "赵六"])
# 1. 索引定位(两种核心方式)
print(s2["张三"]) # 标签索引(自定义索引) 预期输出:85
print(s2[0]) # 位置索引(默认整数位置,从0开始) 预期输出:85
# 2. 数据筛选(按条件过滤)
print(s2[s2 > 85]) # 筛选成绩大于85的数据
"""
预期输出:
李四 92
赵六 90
dtype: int64
"""
print(s2[["张三", "赵六"]]) # 筛选指定索引的数据
# 3. 简单计算(自动对齐索引)
s3 = pd.Series([5, 3, 2, 1], index=["张三", "李四", "王五", "赵六"])
print(s2 + s3) # 相同索引的数据相加,得到新Series
#关键说明:Series的索引定位是核心,标签索引和位置索引需区分清楚;条件筛选支持常见的比较运算符(>、<、==等)。
(2)DataFrame常用操作
DataFrame核心包括行/列查看、数据筛选、简单新增/删除,代码示例如下:
import pandas as pd
data = {
"姓名": ["张三", "李四", "王五", "赵六"],
"年龄": [18, 20, 22, 19],
"成绩": [85, 92, 78, 90]
}
df = pd.DataFrame(data)
# 1. 行/列基础查看
print(df.columns) # 查看所有列名
print(df.index) # 查看所有行索引
print(df.head(2)) # 查看前2行数据(默认前5行)
print(df.tail(2)) # 查看后2行数据
# 2. 数据筛选(按列、按行、按条件)
print(df["姓名"]) # 按列名筛选(提取Series)
print(df[["姓名", "成绩"]]) # 筛选多列(结果为DataFrame)
print(df.iloc[0]) # 按行位置筛选(第1行数据)
print(df[df["成绩"] > 85]) # 按条件筛选(成绩大于85的行)
# 3. 简单新增/删除列
df["排名"] = [3, 1, 4, 2] # 新增"排名"列
print(df)
df_drop = df.drop("排名", axis=1) # 删除"排名"列(axis=1表示按列删除)
print(df_drop)
以上操作是日常数据处理的高频基础操作,建议结合代码反复练习,熟练掌握后能大幅提升数据处理效率。
二、Pandas核心操作理论:数据读取
数据读取是数据处理的第一步,核心目标是将外部数据(如CSV、Excel文件)加载为Pandas的DataFrame格式,以便后续操作;Pandas支持多种数据格式,初学者需重点掌握CSV和Excel两种常用格式的读取逻辑。
1. 核心读取逻辑
Pandas读取数据的本质:通过指定数据文件路径/URL、数据分隔符、索引列等参数,将外部结构化数据解析为DataFrame,核心是“参数匹配数据格式”——即根据外部数据的实际结构,设置对应的读取参数,确保数据正确加载。
2. CSV文件读取(常用)
CSV(逗号分隔值)是最常见的结构化数据格式,数据以逗号为默认分隔符,每行代表一条数据,每列代表一个字段。
核心读取函数:read_csv(),初学者需掌握的核心参数:
filepath_or_buffer:数据路径,可以是本地文件路径(如“./data/titanic.csv”)或网络文件URL(如Hugging Face公开数据集链接)。
sep:数据分隔符,默认是逗号(,),若数据以其他符号分隔(如分号;、制表符\t),需手动指定(如sep=";")。
index_col:指定某一列作为行索引,默认不指定(行索引为0、1、2...),可提高数据定位效率。
header:指定表头行,默认header=0(第一行为列名),若数据无表头,需设置header=None,后续手动指定列名。
usecols:指定需要读取的列,可避免读取无用数据,提升效率(如usecols=["姓名","年龄","成绩"])。
读取后核心验证逻辑:加载数据后需快速确认数据是否正确,核心方式包括:查看前几行数据(确认列名和数据格式)、查看数据基本信息(确认行数、列数、数据类型)、查看是否有缺失值(提前预判后续清洗需求)。
示例代码(本文章使用了huggingface的开源数据集:titanic):
import pandas as pd
# 方法1:读取本地CSV文件(需提前准备titanic.csv文件)
df = pd.read_csv("code/Pandas/data/titanic.csv")
# 也可直接使用url通过网络下载相关数据集
# 方式2:Pandas直接读取公开网络CSV URL
# 泰坦尼克号经典数据集的公开URL(GitHub开源仓库,稳定可用)
# titanic_url = "https://raw.githubusercontent.com/datasciencedojo/datasets/master/titanic.csv"
# 直接读取网络CSV文件(无需本地下载,首次运行需联网)
# df = pd.read_csv(titanic_url)
# 方式3:Seaborn内置数据集
# df = sns.load_dataset('titanic') # Seaborn内置泰坦尼克数据集,自动缓存本地
# 方式4:Hugging Face数据集快捷读取(需先安装datasets库)
# df = pd.read_csv("hf://datasets/ankislyakov/titanic/titanic.csv")
# 可将网络数据集保存到本地
# save_path = "code/Pandas/data/titanic.csv" #实操中记得替换为你实际的地址
# df.to_csv(save_path, index=False) # index=False避免保存多余的索引列
# print("数据集已保存到本地:{save_path}")
# 核心验证操作
print(df.head()) # 查看前5行数据
print(df.info()) # 查看数据基本信息(行数、列数、数据类型、缺失值)
print(df.isnull().sum()) # 单独统计各列缺失值数量
3. Excel文件读取
Excel文件(.xlsx/.xls)是办公场景中常用的数据格式,支持多工作表存储数据,读取时需额外指定工作表信息。
核心读取函数:read_excel(),需掌握的核心参数(补充CSV读取未提及的关键参数):
sheet_name:指定读取的工作表,可传入工作表名称(如sheet_name="Sheet1")或索引(如sheet_name=0,默认读取第一个工作表)。
engine:读取引擎,默认自动选择,若出现读取报错,可手动指定(如读取.xlsx文件用engine="openpyxl",读取.xls文件用engine="xlrd")。
注意事项:读取Excel文件需提前安装对应的依赖库(如openpyxl、xlrd),否则会出现导入失败报错。
# 安装依赖(终端执行)
# pip install openpyxl
# 读取本地Excel文件
df_excel = pd.read_excel("titanic.xlsx", sheet_name="Sheet1")
print(df_excel.head())
三、Pandas核心操作理论:数据清洗
数据清洗是数据处理的核心环节,目标是识别并处理数据中的“脏数据”(缺失值、重复值、异常值、不一致值等),得到干净、可用的标准化数据,为后续分析提供可靠基础;核心原则是“最小干预”,即尽量保留原始数据信息,避免过度处理导致数据失真。
1. 缺失值处理
缺失值是指数据集中存在的空白或未记录的值(如未填写的年龄、缺失的成绩等),是最常见的“脏数据”类型,处理核心是“先识别,后针对性处理”。
(1)缺失值识别:核心思路是通过函数判断数据是否为缺失状态(Pandas中缺失值用NaN表示),常用方式包括:
# 以titanic数据集为例
df = pd.read_csv("code/Pandas/data/titanic.csv")
# 方式1:按列统计缺失值数量
print(df.isnull().sum())
# 方式2:查看缺失值分布(只显示有缺失值的行,前10行)
print(df[df.isnull().any(axis=1)].head(10))
按列统计缺失值数量:明确各字段的缺失程度,为处理方式选择提供依据。
查看缺失值分布:确认缺失值是随机分布还是集中分布(如某一类别数据集中缺失),避免处理后引入偏差。
(2)缺失值处理三大核心方式:
# 方式1:删除法 + 显式生成副本(避免Pandas视图/副本警告,新手必学)
df_clean1 = df.dropna(subset=["Embarked"]).copy()
# 方式2:插值法填充Age(用.loc赋值,明确行/列范围,编码更规范)
# 可选插值方式:linear(线性插值)、pad(向前填充)、bfill(向后填充)、quadratic(二次插值)等
df_clean1.loc[:, "Age"] = df_clean1["Age"].interpolate(method="linear") #线性插值(最常用)
# 方式3:填充法,为“Cabin”列的缺失值填充"Unknown"
df_clean1.loc[:, "Cabin"] = df_clean1["Cabin"].fillna("Unknown")
# 验证处理结果
print(df_clean1.isnull().sum())
删除法:直接删除包含缺失值的行或列,适用于缺失值占比极低(如<5%)、且缺失数据对分析无影响的场景;注意避免大量删除数据导致样本量不足。
填充法:用合理值替换缺失值,适用于缺失值占比中等(5%-30%)的场景,是最常用的处理方式:① 数值型数据:常用均值(适用于数据分布均匀)、中位数(适用于数据存在异常值)填充;② 分类型数据:常用众数(出现频率最高的值)或自定义默认值(如“Unknown”)填充。
插值法:通过数据的趋势或关联关系估算缺失值(如线性插值、基于相邻数据的插值),适用于时间序列数据或存在明显关联的数值型数据,初学者可先掌握基础填充法,后续再深入学习。
2. 重复值处理
重复值是指数据集中完全相同的行(所有字段值均一致),会导致统计结果失真(如重复计算同一数据),处理逻辑相对简单:“识别-删除”。
(1)重复值识别:通过函数判断每行数据是否与之前的行完全重复,统计重复值数量。
# 查看重复行数量
print(df_clean1.duplicated().sum())
# 查看具体重复行(若有)
print(df_clean1[df_clean1.duplicated()])
(2)重复值处理:核心方式是删除重复值,默认保留首次出现的行,删除后续重复行;特殊场景下可根据需求保留最后一次出现的行,或指定某几列作为判断重复的依据(而非所有列)。
# 删除重复行
df_clean2 = df_clean1.drop_duplicates()
# 验证重复值是否删除
print(df_clean2.duplicated().sum()) # 输出0表示无重复值
3. 异常值处理
异常值是指偏离数据正常分布范围的值(如年龄200岁、成绩-10分等),会严重影响统计分析结果(如均值被拉高/拉低),处理核心是“先识别,后判断是否处理”。
(1)异常值识别:
# 方法1:统计描述法(查看Age列的统计信息)
print(df["Age"].describe())
# 方法2:四分位法定义Age列异常值条件
Q1 = df["Age"].quantile(0.25) # 下四分位
Q3 = df["Age"].quantile(0.75) # 上四分位
IQR = Q3 - Q1 # 四分位距
lower_bound = Q1 - 1.5 * IQR # 异常值下限
upper_bound = Q3 + 1.5 * IQR # 异常值上限
abnormal_condition = (df["Age"] < lower_bound) | (df["Age"] > upper_bound) # 异常值标记
print(f"Age列正常范围:{lower_bound:.2f} ~ {upper_bound:.2f}")
print(f"异常值数量:{df[abnormal_condition].shape[0]}")
print(f"异常值占比:{df[abnormal_condition].shape[0]/len(df)*100:.2f}%\n")
"""
预计输出:
统计描述法:
count 891.000000
mean 29.361582
std 13.019697
min 0.420000
25% 22.000000
50% 28.000000
75% 35.000000
max 80.000000
Name: Age, dtype: float64
四分位法:
Age列正常范围:2.50 ~ 54.50
异常值数量:66
异常值占比:7.41%
"""
统计描述法:通过查看数据的统计信息(均值、标准差、最小值、最大值、四分位数等),判断是否存在超出合理范围的值(如年龄最大值为200,明显异常)。
四分位法(IQR法):通过计算四分位距(IQR=上四分位Q3-下四分位Q1),定义异常值范围为“小于Q1-1.5*IQR”或“大于Q3+1.5*IQR”,该方法对数据分布要求低,适用性广。简单概括即:用数据的 “中间 50% 范围” 定义 “正常波动区间”,超出 1.5 倍区间的即为异常。
(2)异常值处理方式:
# 方法1:替换法
df_replace = df.copy()
age_median = df_replace["Age"].median() # 用中位数替换
df_replace.loc[abnormal_condition, "Age"] = age_median
# 验证替换结果
replace_abnormal = (df_replace["Age"] < lower_bound) | (df_replace["Age"] > upper_bound)
print("===== 替换法处理结果 =====")
print(f"替换用的中位数:{age_median:.2f}")
print(f"替换后异常值数量:{df_replace[replace_abnormal].shape[0]}\n")
# 方法2:删除法
df_delete = df.copy()
df_delete = df_delete[~abnormal_condition] # 保留非异常值
print("===== 删除法处理结果 =====")
print(f"删除前总行数:{len(df)}")
print(f"删除后总行数:{len(df_delete)}")
print(f"删除的异常值行数:{len(df)-len(df_delete)}\n")
# 方法3:修正法(截断到正常范围)
df_fix = df.copy()
df_fix.loc[df_fix["Age"] < lower_bound, "Age"] = lower_bound # 低于下限→下限
df_fix.loc[df_fix["Age"] > upper_bound, "Age"] = upper_bound # 高于上限→上限
# 验证修正结果
fix_abnormal = (df_fix["Age"] < lower_bound) | (df_fix["Age"] > upper_bound)
print("===== 修正法处理结果 =====")
print(f"修正后异常值数量:{df_fix[fix_abnormal].shape[0]}\n")
# 方法4:保留法(仅标注,不修改)
df_keep = df.copy()
df_keep["Age_Is_Abnormal"] = abnormal_condition # 新增列标注异常值
print("===== 保留法处理结果 =====")
print("异常值标注列统计(正常/异常):")
print(df_keep["Age_Is_Abnormal"].value_counts())
删除法:适用于异常值明确是错误数据(如录入错误)、且数量极少的场景。
修正法:若异常值是可修正的错误(如将“200岁”修正为“20岁”),可通过人工核查或规则修正。
替换法:用均值、中位数等合理值替换异常值,适用于异常值数量较少、但删除会影响样本完整性的场景。
保留法:若异常值是真实存在的特殊情况(如某商品的极端高销量),需保留并在后续分析中单独标注说明。
四、Pandas核心操作理论:分组统计
分组统计是数据分析的核心手段,核心思路是“按指定条件将数据分组,对每组数据进行聚合计算”,实现从整体数据到分组细节数据的挖掘,常用场景包括“按类别统计均值”“按时间段统计总和”等。
1. 分组统计核心逻辑(Split-Apply-Combine)
Pandas的分组统计遵循“拆分-应用-合并”三步流程,是理解分组操作的关键:
# 以titanic清洗后的数据为例,按Sex分组统计Age的均值
# Split(拆分):按Sex拆分为男性和女性两个子DataFrame
# Apply(应用):计算每个子DataFrame中Age的均值
# Combine(合并):将结果合并为新的DataFrame
print("Step1:Split")
# 按Sex列把数据拆分成「女性组」和「男性组」
grouped = df.groupby("Sex")
for group_name, group_data in grouped:
print(f"分组名称:{group_name},该组数据行数:{len(group_data)}")
print("\nStep2:Apply")
# 对每个分组的Age列,执行“计算均值”的操作
# 本质:分别算女性组Age均值、男性组Age均值
group_age_mean = grouped["Age"].mean()
print("\nStep3:Combine")
# 自动把两个分组的均值结果,合并成一个新的表格(Series)
print("按性别分组的Age均值最终结果:")
print(group_age_mean)
print("\n拓展:一次统计多个指标(均值+中位数)")
# Apply:同时计算均值和中位数
# Combine:合并成带列名的表格
group_age_stats = grouped["Age"].agg(["mean", "median"])
print("按性别分组的Age均值+中位数:")
print(group_age_stats)
运行结果:
Step1:Split
分组名称:female,该组数据行数:314
分组名称:male,该组数据行数:577
Step2:Apply
Step3:Combine
按性别分组的Age均值最终结果:
Sex
female 27.929936
male 30.140676
Name: Age, dtype: float64
拓展:一次统计多个指标(均值+中位数)
按性别分组的Age均值+中位数:
mean median
Sex
female 27.929936 28.0
male 30.140676 28.0
2. 分组条件的类型
分组条件决定了数据的拆分方式,初学者需掌握三种常见分组类型:
# 1. 单一条件分组(按Sex分组,统计存活人数)
single_group = df.groupby("Sex")["Survived"].sum()
# 2. 多条件分组(按Sex+Pclass分组,统计存活人数)
multi_group = df.groupby(["Sex", "Pclass"])["Survived"].sum()
# 3. 自定义条件分组(按年龄范围分组,统计平均票价)
# 先定义分组规则
def age_group(age):
if age < 18:
return "未成年"
elif 18 <= age <= 60:
return "成年"
else:
return "老年"
# 新增年龄分组列
df["Age_Group"] = df["Age"].apply(age_group)
# 按自定义分组统计
custom_group = df.groupby("Age_Group")["Fare"].mean()
print("单一条件分组:")
print(single_group)
print("\n多条件分组:")
print(multi_group)
print("\n自定义条件分组:")
print(custom_group)
运行结果:
单一条件分组:
Sex
female 233
male 109
Name: Survived, dtype: int64
多条件分组:
Sex Pclass
female 1 91
2 70
3 72
male 1 45
2 17
3 47
Name: Survived, dtype: int64
自定义条件分组:
Age_Group
成年 32.084434
未成年 31.220798
老年 41.371214
Name: Fare, dtype: float64
单一条件分组:按某一个字段的值分组(如按“性别”分组、按“班级”分组),是最基础的分组方式。
多条件分组:按多个字段的组合条件分组(如按“性别+舱位等级”分组、按“班级+学科”分组),可实现更细致的统计分析。
自定义条件分组:按自定义规则分组(如按年龄范围分组:<18岁、18-30岁、>30岁;按数值区间分组:低、中、高),适用于需要灵活划分数据的场景。
3. 常用聚合操作
聚合操作是分组后对每组数据的计算,核心是“对数值型数据进行汇总或描述”,常用聚合函数及用途:
# 按Sex分组执行多聚合操作
agg_result = df.groupby("Sex").agg(
Age_mean=("Age", "mean"),
Age_median=("Age", "median"),
Age_max=("Age", "max"),
Fare_sum=("Fare", "sum"),
Fare_total_count=("Fare", "size"), # size统计总行数(含缺失值),count只统计非空
Survived_sum=("Survived", "sum")
)
# 打印结果
print("按性别分组的聚合统计结果:")
print(agg_result)
运行结果:
按性别分组的聚合统计结果:
Age_mean Age_median Age_max Fare_sum Fare_total_count Survived_sum
Sex
female 27.929936 28.0 63.0 13966.6628 314 233
male 30.140676 28.0 80.0 14727.2865 577 109
基础统计聚合:sum(求和,如统计每组总销量)、mean(求均值,如统计每组平均年龄)、count(计数,如统计每组人数)、max(求最大值)、min(求最小值)、std(求标准差,反映数据离散程度)。
进阶统计聚合:median(求中位数,适用于存在异常值的数据)、quantile(求四分位数,分析数据分布)、unique(统计每组唯一值,适用于分类型数据)、nunique(统计每组唯一值数量)。
五、总结
1. 核心数据结构:掌握Series(一维带标签数组)与DataFrame(二维表格数据)的定义、特点及关联,是学习Pandas的基础。
2. 数据读取:理解read_csv()/read_excel()的核心参数逻辑,明确“参数匹配数据格式”和“读取后验证”的重要性。
3. 数据清洗:掌握缺失值、重复值、异常值的“识别-处理”核心思路,牢记“最小干预”原则,根据数据情况选择合适处理方式。
4. 分组统计:理解“Split-Apply-Combine”三步流程,掌握常见分组条件和聚合操作,明确分组统计的核心目标是挖掘分组数据规律。
参考资料:Pandas官方文档:https://pandas.pydata.org/docs/
数据集资源:ankislyakov/titanic · Datasets at Hugging Face(需科学上网)
更多推荐

所有评论(0)