深入了解 Pandas 中的层次化索引(Hierarchical Indexing)

层次化索引(Hierarchical Indexing)是 Pandas 中一种用于处理多维数据的重要功能。它允许在一个轴上拥有多个(两个或更多)索引级别,从而能够更灵活地表示和操作高维数据。

创建多层索引

隐式构造创建多层索引

1.通过给DataFrame构造函数的index参数传递两个或更多的数组
import numpy as np
import pandas as pd
from pandas import DataFrame, Series

columns = [['期中', '期中', '期中', '期中', '期末', '期末', '期末', '期末'], ['语文', '数学', '英语', '综合', '语文', '数学', '英语', '综合']]
index = [['一班', '一班', '一班', '一班', '一班', '二班', '二班','二班', '二班', '二班'], 
         ['张三', '李四', '王五', '赵六', '田七', '孙八', '钱九', '陈十', '赵四', '小明']]
data = np.random.randint(0, 150, size=(10, 8))
df = DataFrame(index=index, data=data, columns=columns)
df
期中期末
语文数学英语综合语文数学英语综合
一班张三616811353171119624
李四196313875668778124
王五5140501411111077895
赵六4030263513910071122
田七23113147106874810830
二班孙八107206511219387334
钱九13813577103927930
陈十249110951034919108
赵四3125221341011210073
小明82551241557127
扩展:series也可以创建多层索引
# Series也可以创建多层索引
index = [['一班', '一班', '一班', '一班', '一班', '二班', '二班','二班', '二班', '二班'], 
         ['张三', '李四', '王五', '赵六', '田七', '孙八', '钱九', '陈十', '赵四', '小明']]

data = np.random.randint(0, 150, size=(10, ))
s = Series(data=data, index=index)
s
index = [['一班', '一班', '一班', '一班', '一班', '二班', '二班','二班', '二班', '二班'], 
         ['张三', '李四', '王五', '赵六', '田七', '孙八', '钱九', '陈十', '赵四', '小明']]

data = np.random.randint(0, 150, size=(10, ))
s = Series(data=data, index=index)
s
"""
一班  张三    123
    李四     19
    王五    117
    赵六     32
    田七     61
二班  孙八    123
    钱九     90
    陈十     38
    赵四    114
    小明     14
dtype: int32
"""

显示构造pd.MultiIndex创建多层索引

1.使用数组
columns = pd.MultiIndex.from_arrays([['期中', '期中', '期中', '期中', '期末', '期末', '期末', '期末'], ['语文', '数学', '英语', '综合', '语文', '数学', '英语', '综合']])
index = pd.MultiIndex.from_arrays([['一班', '一班', '一班', '一班', '一班', '二班', '二班','二班', '二班', '二班'], 
         ['张三', '李四', '王五', '赵六', '田七', '孙八', '钱九', '陈十', '赵四', '小明']])
data = np.random.randint(0, 150, size=(10, 8))
df = DataFrame(index=index, columns=columns, data=data)
df
期中期末
语文数学英语综合语文数学英语综合
一班张三6654642197046140
李四615185231183713584
王五146461422311583759
赵六91694175514414885
田七4135364012631102143
二班孙八1321471512659976243
钱九1301489960111126864
陈十32731294073756086
赵四104569513079704927
小明107541437728125119118
2.使用tuple
columns = pd.MultiIndex.from_tuples((('期中', '语文'), ('期中', '英语'), ('期中', '数学'), ('期中','综合'), ('期末', '语文'), ('期末', '英语'), ('期末', '数学'), ('期末','综合')))
index = [['一班', '一班', '一班', '一班', '一班', '二班', '二班','二班', '二班', '二班'], 
         ['张三', '李四', '王五', '赵六', '田七', '孙八', '钱九', '陈十', '赵四', '小明']]
data = np.random.randint(0, 150, size=(10, 8))
df = DataFrame(index=index, columns=columns, data=data)
df
期中期末
语文英语数学综合语文英语数学综合
一班张三40128631095892127108
李四66541317761347367
王五6469102114341568145
赵六6405448122133859
田七1186325121041116033
二班孙八603967307429133124
钱九941617414314574111
陈十148391124513751128144
赵四131132247429527139
小明236184401116114114
3.使用product(推荐使用)
columns = pd.MultiIndex.from_product([['期中', '期末'], ['语文', '数学', '英语', '综合']])
index = [['一班', '一班', '一班', '一班', '一班', '二班', '二班','二班', '二班', '二班'], 
         ['张三', '李四', '王五', '赵六', '田七', '孙八', '钱九', '陈十', '赵四', '小明']]
data = np.random.randint(0, 150, size=(10, 8))
df = DataFrame(index=index, columns=columns, data=data)
df
期中期末
语文数学英语综合语文数学英语综合
一班张三1345914013141965592
李四9023447113429621
王五71333996693130144
赵六35292129534487129
田七109104114104658819101
二班孙八12354246854614669
钱九10925149138925094109
陈十14263393959626372
赵四761611414010212442147
小明791001031278153145

多层索引对象的索引与切片操作

Series索引与切片

s
"""
一班  张三    123
    李四     19
    王五    117
    赵六     32
    田七     61
二班  孙八    123
    钱九     90
    陈十     38
    赵四    114
    小明     14
dtype: int32
"""

# 显式索引, 多层索引的原则: 一定要从最外层索引往内层走
s.loc['一班']
"""
张三    123
李四     19
王五    117
赵六     32
田七     61
dtype: int32
"""

# 多层索引建议括号括起来. 
s.loc[('一班', '张三')] # 123

# 隐式索引
s.iloc[0] #  123
# 显式切片
s.loc['一班': '二班']
"""
一班  张三    123
    李四     19
    王五    117
    赵六     32
    田七     61
二班  孙八    123
    钱九     90
    陈十     38
    赵四    114
    小明     14
dtype: int32
"""

# 不建议多层索引进行内层索引的切片
# s.loc[('一班', '张三'): ('二班', '钱九')] # 异常

# 建议使用隐式索引. 
s.iloc[:7]
"""
一班  张三    123
    李四     19
    王五    117
    赵六     32
    田七     61
二班  孙八    123
    钱九     90
dtype: int32
"""

DataFrame索引与切片

columns = pd.MultiIndex.from_product([['期中', '期末'], ['语文', '数学', '英语']])
index = [['一班', '一班', '一班', '二班', '二班','二班', ], 
         ['张三', '李四', '王五', '赵六', '田七', '孙八', ]]
data = np.random.randint(0, 150, size=(6, 6))
df = DataFrame(index=index, columns=columns, data=data)
df
期中期末
语文数学英语语文数学英语
一班张三147119772739103
李四124111414846135
王五1326413102134137
二班赵六1367534192369
田七4777115125294
孙八11522118239864
1.列索引与切片
# 显式索引, 直接中括号
df['期中', '语文'] # 返回Series

# 推荐使用括号括起来.
df[('期中', '语文')] # 返回Series

"""
一班  张三    147
    李四    124
    王五    132
二班  赵六    136
    田七     47
    孙八    115
Name: (期中, 语文), dtype: int32
"""

# 隐式的列索引
df.iloc[:, 0]
"""
一班  张三    147
    李四    124
    王五    132
二班  赵六    136
    田七     47
    孙八    115
Name: (期中, 语文), dtype: int32
"""
# 列的显式索引切片虽然不报错, 但是没有内容. 
df['期中': '期末']
期中期末
语文数学英语语文数学英语
# 推荐使用隐式索引去切片
df.iloc[:, 1:4]
期中期末
数学英语语文
一班张三1197727
李四1114148
王五6413102
二班赵六753419
田七7711512
孙八2211823
2.行索引与切片

行索引推荐使用loc()函数(使代码更加清晰和易于理解)

# 行索推荐用.loc
df.loc['一班']
期中期末
语文数学英语语文数学英语
张三147119772739103
李四124111414846135
王五1326413102134137
# 不能直接索引内层索引
# df.loc['张三'] # KeyError: '张三'

df.loc['一班','张三'] # 返回Series

# 建议多层索引用括号括起来. 
df.loc[('一班','张三')] # 返回Series

"""
期中  语文    147
    数学    119
    英语     77
期末  语文     27
    数学     39
    英语    103
Name: (一班, 张三), dtype: int32
"""

# 隐式索引 找第0行
df.iloc[0]
"""
期中  语文    147
    数学    119
    英语     77
期末  语文     27
    数学     39
    英语    103
Name: (一班, 张三), dtype: int32
"""
# 行切片
df.loc['一班': '二班']
期中期末
语文数学英语语文数学英语
一班张三147119772739103
李四124111414846135
王五1326413102134137
二班赵六1367534192369
田七4777115125294
孙八11522118239864
# 推荐使用隐式索引去完成切片
df.iloc[0:5]
期中期末
语文数学英语语文数学英语
一班张三147119772739103
李四124111414846135
王五1326413102134137
二班赵六1367534192369
田七4777115125294
# 元素的索引. 永远都是先索引行, 再索引列. 
df.loc[('一班', '张三'), ('期中', '语文')] # 147

# 隐式写法
df.iloc[0, 0] # 147
147

注意在对行索引的时候,若一级行索引还有多个,对二级行索引会遇到问题!也就是说,无法直接对二级索引进行索引,必须让二级索引变成一级索引后才能对其进行索引!

# 如果要使用‘一班’中所有同学名字的二级索引
df1 = df.loc['一班']
df1
期中期末
语文数学英语语文数学英语
张三147119772739103
李四124111414846135
王五1326413102134137
# 此时df1拿到了‘一班’所有同学成绩,同学名字作为1级索引
# 此时可以使用'同学名字'直接索引
df1.loc['张三']
"""
期中  语文    147
    数学    119
    英语     77
期末  语文     27
    数学     39
    英语    103
Name: 张三, dtype: int32
"""
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值