在一个级别和每个分区按较早级别对索引进行排序
Sort index at a level and per partitioning by earlier levels
我正在使用 pandas 来计算不同的类型或错误并纠正不同(机器学习)模型的预测,以显示混淆矩阵。
预测和基本事实标签的特定顺序是有意义的,例如将多数 class 'B' 放在第一位。
但是,当我使用 pd.DataFrame.sort_index
排序时,其他索引级别也被排列。我想根据第一个索引的唯一值对第二级进行排序。
errors = pd.DataFrame([
{'model': model, 'ground truth': ground_truth, 'prediction': prediction,
'count': np.random.randint(0, (10000 if prediction=='B' else 1000) if prediction==ground_truth else 100)}
for model in ['foo', 'bar']
for prediction in 'ABC'
for ground_truth in 'ABC'
])
def sort_index(index):
return index.map('BCA'.index)
errors.pivot(
index=['model', 'ground truth'],
columns=['prediction'],
values='count'
).fillna(0).astype(int).sort_index(level=1, key=sort_index)[['B', 'C', 'A']]
一种解决方案是也按所有较早的索引进行排序,但它非常冗长。将一个函数应用于所有索引是愚蠢的,就好像它们在语义上都是相同的一样。此外,这还会重新排列模型的顺序,这并不是必需的。最后,它在两个方面浪费了计算:对较小的分区进行排序速度更快,因为排序超线性缩放,并且在考虑更多索引时元素比较更慢。
def sort_index(index):
if index.name == 'ground truth':
return index.map('BCA'.index)
return index
errors.pivot(
index=['model', 'ground truth'],
columns=['prediction'],
values='count'
).fillna(0).astype(int).sort_index(level=[0, 1], key=sort_index)[['B', 'C', 'A']]
是否有一种干净的方法来对较高的索引级别进行排序,同时将较早的级别保持在一起?
您可能想使用 reindex
方法。
代码:
import numpy as np
import pandas as pd
# Create a sample dataframe
errors = pd.DataFrame([ {'model': model, 'ground truth': ground_truth, 'prediction': prediction, 'count': np.random.randint(0, (10000 if prediction=='B' else 1000) if prediction==ground_truth else 100)} for model in ['foo', 'bar'] for prediction in 'ABC' for ground_truth in 'ABC' ])
# Pivot and reindex the dataframe
errors.pivot(
index=['model', 'ground truth'],
columns=['prediction'],
values='count'
).fillna(0).astype(int).reindex(['B', 'C', 'A'], level=1)[['B', 'C', 'A']]
输出:
我正在使用 pandas 来计算不同的类型或错误并纠正不同(机器学习)模型的预测,以显示混淆矩阵。
预测和基本事实标签的特定顺序是有意义的,例如将多数 class 'B' 放在第一位。
但是,当我使用 pd.DataFrame.sort_index
排序时,其他索引级别也被排列。我想根据第一个索引的唯一值对第二级进行排序。
errors = pd.DataFrame([
{'model': model, 'ground truth': ground_truth, 'prediction': prediction,
'count': np.random.randint(0, (10000 if prediction=='B' else 1000) if prediction==ground_truth else 100)}
for model in ['foo', 'bar']
for prediction in 'ABC'
for ground_truth in 'ABC'
])
def sort_index(index):
return index.map('BCA'.index)
errors.pivot(
index=['model', 'ground truth'],
columns=['prediction'],
values='count'
).fillna(0).astype(int).sort_index(level=1, key=sort_index)[['B', 'C', 'A']]
一种解决方案是也按所有较早的索引进行排序,但它非常冗长。将一个函数应用于所有索引是愚蠢的,就好像它们在语义上都是相同的一样。此外,这还会重新排列模型的顺序,这并不是必需的。最后,它在两个方面浪费了计算:对较小的分区进行排序速度更快,因为排序超线性缩放,并且在考虑更多索引时元素比较更慢。
def sort_index(index):
if index.name == 'ground truth':
return index.map('BCA'.index)
return index
errors.pivot(
index=['model', 'ground truth'],
columns=['prediction'],
values='count'
).fillna(0).astype(int).sort_index(level=[0, 1], key=sort_index)[['B', 'C', 'A']]
是否有一种干净的方法来对较高的索引级别进行排序,同时将较早的级别保持在一起?
您可能想使用 reindex
方法。
代码:
import numpy as np
import pandas as pd
# Create a sample dataframe
errors = pd.DataFrame([ {'model': model, 'ground truth': ground_truth, 'prediction': prediction, 'count': np.random.randint(0, (10000 if prediction=='B' else 1000) if prediction==ground_truth else 100)} for model in ['foo', 'bar'] for prediction in 'ABC' for ground_truth in 'ABC' ])
# Pivot and reindex the dataframe
errors.pivot(
index=['model', 'ground truth'],
columns=['prediction'],
values='count'
).fillna(0).astype(int).reindex(['B', 'C', 'A'], level=1)[['B', 'C', 'A']]