我遇到了一个非常奇怪的问题,或者我可以说是一个bug,当处理一些类别与字符串Dtype时。看看这个简单的示例 Dataframe :
import pandas as pd
import numpy as np
data = pd.DataFrame({
'status' : ['pending', 'pending','pending', 'canceled','canceled','canceled', 'confirmed', 'confirmed','confirmed'],
'partner' : ['A', np.nan,'C', 'A',np.nan,'C', 'A', np.nan,'C'],
'product' : ['afiliates', 'pre-paid', 'giftcard','afiliates', 'pre-paid', 'giftcard','afiliates', 'pre-paid', 'giftcard'],
'brand' : ['brand_1', 'brand_2', 'brand_3','brand_1', 'brand_2', 'brand_3','brand_1', 'brand_2', 'brand_3'],
'gmv' : [100,100,100,100,100,100,100,100,100]})
data = data.astype({'partner':'category','status':'category','product':'category', 'brand':'category'})
执行单个位置选择时
test = data.loc[(data.partner !='A') | ((data.brand == 'A') & (data.status == 'confirmed'))]
这是输出
现在,只需将我的分类列移到string(我将它移回string,因为有一个与groupby有关的问题,如here所述)
data = data.astype({'partner':'string','status':'string','product':'string', 'brand':'string'})
以免发出同样的锁定命令。
test2 = data.loc[(data.partner !='A') | ((data.brand == 'A') & (data.status == 'confirmed'))]
但是看看输出!
我真的不知道为什么它不起作用。我已经弄清楚了这是与被送回字符串的NAN范畴有关的东西,但我不明白为什么这会是一个问题。
1条答案
按热度按时间vlurs2pr1#
问题恰恰在于类别类型和字符串类型中的NAN值之间的差异:
对于category,nan值的类型是'float'(作为典型的nan),您可以在比较中使用它,因此:
data.partner !='A'
对于所有具有NaN的行都将为True。当类型转换为字符串时,nan值的类型转换为panda._libs.missing.NAType,您不能在比较中使用此类型,因此现在:
data.partner !='A'
返回非True的值,并且结果不同。基本上,类别类型中的NaN本身不是一个类别,所以它的处理方式不同。这就是为什么你不能在类别上使用fillna,你必须为它定义一个类别值。你可以使用如下代码:
添加一个自定义的NA类别并替换丢失的值。现在,如果转换为字符串并运行相同的条件,您应该会得到相同的结果。