通过迭代大熊猫数据帧中的行来添加虚拟列

时间:2015-12-07 19:29:31

标签: python-3.x numpy pandas dataframe

我有一个像这样的pandas数据框(X11):

    dx1      dx2    dx3    dx4    
0   25041   40391   5856    0     
1   25041   40391   25081   5856  
2   25041   40391   42822   0     
3   25061   40391   0       0     
4   25041   40391   0       5856  
5   40391   25002   5856    3569 

我想为25041,40391,5856等单元格值创建虚拟列。因此,如果25041出现在任何dxs列中的特定行中,则会有一个值为250或0的列25041。我正在使用此代码,当行数较少时,它可以正常工作。最终结果在底部。

mat = X11.as_matrix(columns=None)
values, counts = np.unique(mat.astype(str), return_counts=True)

for x in values:
    X11[x] = X11.isin([x]).any(1).astype(int)

当行数是数千或数百万时,它会挂起并永远消失,我没有得到任何结果。

然后我开始使用这段代码:@michaelg建议

colN_d = X11.columns.values

for column_name in colN_d:
    dummies = pd.get_dummies(X11[column_name])
    print(column_name, dummies)
    col_names_dummies = dummies.columns.values
    print(col_names_dummies)

    #then you can append new columns to the dataframe
    for i,value in enumerate(col_names_dummies):
        X11[value] = dummies.iloc[:,i]

这会生成虚拟列,但是对于那些出现在多列中的虚拟变量,如40391(出现在dx1和dx2中),0,5856(出现在dx3& dx4),它会生成多个虚拟对象并覆盖之前的虚拟列(s )由相同的名称生成,因此我松散行值。像这样:

dx1    25041  25061  40391
0      1      0      0
1      1      0      0
2      1      0      0
3      0      1      0
4      1      0      0
5      0      0      1
['25041' '25061' '40391']
dx2    25002  40391
0      0      1
1      0      1
2      0      1
3      0      1
4      0      1
5      1      0
['25002' '40391']
dx3    0  25081  42822  5856
0  0      0      0     1
1  0      1      0     0
2  0      0      1     0
3  1      0      0     0
4  1      0      0     0
5  0      0      0     1
[0 '25081' '42822' '5856']
dx4    0  3569  5856
0  1     0     0
1  0     0     1
2  1     0     0
3  1     0     0
4  0     0     1
5  0     1     0
[0 '3569' '5856']

最终结果如下:这是不正确的,不符合我的期望

dx1     dx2     dx3     dx4     25041   25061   40391   25002   0   25081   
25041   40391   5856    0       1       0       1       0       1   0   
25041   40391   25081   5856    1       0       1       0       0   1   
25041   40391   42822   0       1       0       1       0       1   0   
25061   40391   0       0       0       1       1       0       1   0   
25041   40391   0       5856    1       0       1       0       0   0   
40391   25002   5856    3569    0       0       0       1       0   0   

您可以看到40391出现在所有行中,因此它应该在所有行中都有1。但如上所述,该程序创建了两个具有相同名称的假人,最后一个包含在此中。而两个事件的联盟都应该满足要求。对于列' 0'同样如此。

它应该是这样的:这是正确的,输出应该是这样的。

dx1     dx2     dx3    dx4  0   25002   25041   25061   25081   3569    40391   42822   5856
25041   40391   5856    0   0   0       1       0       0       0          1        0       1
25041   40391   25081  5856 0   0       1       0       1       0            1      0       1
25041   40391   42822   0   0   0       1       0       0       0           1       1       0
25061   40391   0       0   0   0       0       1       0       0          1        0       0
25041   40391   0    5856   0   0       1       0       0       0          1        0       1
40391   25002 5856   3569   0   1       0       0       0       1          1        0       1

有没有办法根据我的要求有效地创建虚拟列? 知道如何改进上面提到的逻辑吗?

0 个答案:

没有答案