0

我有一个包含 2 列有序分类数据(相同类别)的 DataFrame。我想构建另一列,其中包含前 2 列的分类最大值。我设置了以下。

import pandas as pd
from pandas.api.types import CategoricalDtype
import numpy as np

cats = CategoricalDtype(categories=['small', 'normal', 'large'], ordered=True)
data = {
    'A': ['normal', 'small', 'normal', 'large', np.nan],
    'B': ['small', 'normal', 'large', np.nan, 'small'],
    'desired max(A,B)': ['normal', 'normal', 'large', 'large', 'small']
}
df = pd.DataFrame(data).astype(cats)

尽管 np.nan 项有问题,但可以比较列,如运行以下代码所示。

df['A'] > df['B']

该手册建议 max() 适用于分类数据,因此我尝试按如下方式定义我的新列。

df[['A', 'B']].max(axis=1)

这会产生一列 NaN。为什么?

4

2 回答 2

0

以下代码使用分类列的可比性构造所需的列。我仍然不知道为什么 max() 在这里失败。

dfA = df['A']
dfB = df['B']
conditions = [dfA.isna(), (dfB.isna() | (dfA >= dfB)), True]
cases = [dfB, dfA, dfB]
df['maxAB'] = np.select(conditions, cases)
于 2020-03-23T11:10:54.013 回答
0

A 列和 B 列是字符串类型。Max 无法理解 ['small', 'medium', 'large'] 中哪个是最大的。因此,您必须首先为这些类别中的每一个分配整数值。

# size string -> integer value mapping
size2int_map = {
    'small': 0, 
    'normal': 1, 
    'large': 2
}

# integer value -> size string mapping
int2size_map = {
    0: 'small', 
    1: 'normal', 
    2: 'large'
}

# create columns containing the integer value for each size string
for c in df:
    df['%s_int' % c] = df[c].map(size2int_map)

# apply the int2size map back to get the string sizes back
print(df[['A_int', 'B_int']].max(axis=1).map(int2size_map))

你应该得到

0    normal
1    normal
2     large
3     large
4     small
dtype: object
于 2020-03-18T21:35:06.580 回答