如何在pandas数据框中移动列
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了如何在pandas数据框中移动列相关的知识,希望对你有一定的参考价值。
我想把一个索引为'length'的列,并将其作为我的第二列。它目前作为第5列存在。我试过了:
colnames = big_df.columns.tolist()
# make index "length" the second column in the big_df
colnames = colnames[0] + colnames[4] + colnames[:-1]
big_df = big_df[colnames]
我看到以下错误:
TypeError:必须是str,而不是list
我不知道如何解释这个错误,因为它实际上应该是一个list
,对吧?
另外,是否有通用方法将任何列按标签移动到指定位置?我的专栏只有一个级别,即没有涉及MultiIndex
。
Correcting your error
我不确定如何解释这个错误,因为它实际上应该是一个列表,对吧?
不:colnames[0]
和colnames[4]
是标量,而不是列表。您无法将标量与列表连接起来。要使它们成为列表,请使用方括号:
colnames = [colnames[0]] + [colnames[4]] + colnames[:-1]
此外,我强烈建议你使用df.columns = colnames
而不是df[[colnames]]
:__getitem__
(或其语法糖[]
)triggers a copy operation。
Generic solution
但是将数组转换为列表然后手动连接列表不仅昂贵,而且容易出错。 related answer有许多基于列表的解决方案,但基于NumPy的解决方案是值得的,因为pd.Index
对象存储为NumPy数组。
这里的关键是通过切片而不是连接来修改NumPy数组。只处理2种情况:当前位置后存在所需位置时,反之亦然。
import pandas as pd, numpy as np
from string import ascii_uppercase
df = pd.DataFrame(columns=list(ascii_uppercase))
def shifter(df, col_to_shift, pos_to_move):
arr = df.columns.values
idx = df.columns.get_loc(col_to_shift)
if idx == pos_to_move:
pass
elif idx > pos_to_move:
arr[pos_to_move+1: idx+1] = arr[pos_to_move: idx]
else:
arr[idx: pos_to_move] = arr[idx+1: pos_to_move+1]
arr[pos_to_move] = col_to_shift
df.columns = arr
return df
df = df.pipe(shifter, 'J', 1)
print(df.columns)
Index(['A', 'J', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'K', 'L', 'M', 'N',
'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z'],
dtype='object')
Performance benchmarking
对于大量列而不是基于列表的方法,使用NumPy切片更有效:
n = 10000
df = pd.DataFrame(columns=list(range(n)))
def shifter2(df, col_to_shift, pos_to_move):
cols = df.columns.tolist()
cols.insert(pos_to_move, cols.pop(df.columns.get_loc(col_to_shift)))
df.columns = cols
return df
%timeit df.pipe(shifter, 590, 5) # 381 µs
%timeit df.pipe(shifter2, 590, 5) # 1.92 ms
以上是关于如何在pandas数据框中移动列的主要内容,如果未能解决你的问题,请参考以下文章
如何对一列执行 pandas groupby 操作,但将另一列保留在结果数据框中
如何判断 pandas 数据框中的列是不是为 datetime 类型?如何判断一列是不是为数字?