如何从熊猫的给定行中删除仅包含零的列

时间:2019-03-20 12:02:37

标签: python pandas

我已经找到了如何使用命令df.loc[:, (df != 0).any(axis=0)]删除所有行的零列,我需要做同样的事情,但是要给出行号。

例如,对于以下df

In [75]: df = pd.DataFrame([[1,1,0,0], [1,0,1,0]], columns=['a','b','c','d'])

In [76]: df                                                                                                                                                                            
Out[76]: 
   a  b  c  d
0  1  1  0  0
1  1  0  1  0

给我第0行的非零列,我希望得到结果:

   a  b
0  1  1

对于第1行,得到:

   a  c
1  1  1

我尝试了很多命令组合,但是找不到解决方案。

更新:

我有一个300x300的矩阵,我需要更好地可视化其结果。

下面的伪代码试图显示我的需求

for i in range(len(df[rows])):
  _df = df.iloc[i]
  _df = _df.filter(remove_zeros_columns)
  print('Row: ', i)
  print(_df)

结果:

Row: 0
   a  b
0  1  1

Row: 1
   a  c  f
1  1  5  10

Row: 2
   e
2  20

最好的问候。 克莱森里奥斯(Kleyson Rios)。

3 个答案:

答案 0 :(得分:3)

您可以更改数据结构:

df = df.reset_index().melt('index', var_name='columns').query('value != 0')
print (df)
   index columns  value
0      0       a      1
1      1       a      1
2      0       b      1
5      1       c      1

如果需要用由,联接的值来新建一列,请比较不等于DataFrame.ne的值,并使用DataFrame.dot进行矩阵乘法:

df['new'] = df.ne(0).dot(df.columns + ', ').str.rstrip(', ')
print (df)
   a  b  c  d   new
0  1  1  0  0  a, b
1  1  0  1  0  a, c

编辑:

for i in df.index:
    row = df.loc[[i]]

    a = row.loc[:, (row != 0).any()]
    print ('Row {}'.format(i))
    print (a)

或者:

def f(x):
    print ('Row {}'.format(x.name))
    print (x[x!=0].to_frame().T)

df.apply(f, axis=1)

Row 0
   a  b
0  1  1
Row 1
   a  c
1  1  1

答案 1 :(得分:2)

df = pd.DataFrame([[1, 1, 0, 0], [1, 0, 1, 0]], columns=['a', 'b', 'c', 'd'])


def get(row):

    return list(df.columns[row.ne(0)])


df['non zero column'] = df.apply(lambda x: get(x), axis=1)
print(df)

如果您想使用单眼线笔,也请使用

df['non zero column'] = [list(df.columns[i]) for i in df.ne(0).values]

输出

   a  b  c  d non zero column
0  1  1  0  0          [a, b]
1  1  0  1  0          [a, c]

答案 2 :(得分:0)

我认为这可以更严格地回答您的问题。 只需根据需要更改Given_row的值即可。

given_row = 1
mask_all_rows = df.apply(lambda x: x!=0, axis=0)
mask_row = mask_all_rows.loc[given_row]
cols_to_keep = mask_row.index[mask_row == True].tolist()
df_filtered = df[cols_to_keep]

# And if you only want to keep the given row
df_filtered = df_filtered[df_filtered.index == given_row]