2012-06-16 195 views
134

我有一個dataframe,列數超過200列(不要問爲什麼)。這個問題是因爲他們產生的順序Python Pandas - 根據列名重新排列數據框中的列

['Q1.3','Q6.1','Q1.2','Q1.1',......] 

我需要重新排序的列如下:

['Q1.1','Q1.2','Q1.3',.....'Q6.1',......] 

是否有某種方式爲我蟒蛇內做到這一點?

+16

爲什麼你有200列嗎? ;) –

+0

可能重複的[如何更改DataFrame列的順序?](https://stackoverflow.com/questions/13148429/how-to-change-the-order-of-dataframe-columns) –

回答

171
df.reindex_axis(sorted(df.columns), axis=1) 

這假設對列名進行排序會給出您想要的訂單。如果列名不按字典順序排序(例如,如果您希望列Q10.3出現在Q9.1之後),則需要進行不同的排序,但與大熊貓無關。

+2

我喜歡這個因爲可以使用相同的方法對行進行排序(我需要對行和列進行排序)。雖然它是相同的方法,但您可以省略'axis'參數(或提供其默認值'0'),如'df.reindex_axis(sorted(non_sorted_row_index))',相當於'df.reindex(sorted(non_sorted_row_index) ))' –

+0

請注意,重新索引不是在原地完成的,因此要將這種排序實際應用於df,您必須使用'df = df.reindex_axis(...)'。另外,請注意,使用這種方法很容易實現非詞典排序,因爲列名稱列表可以單獨排序爲任意順序,然後傳遞給'reindex_axis'。這是@Wes McKinney('df = df.sort_index(axis = 1)')建議的替代方法所不可能的,但這對於純粹的詞典編排來說是更清晰的。 – WhoIsJack

0

sort方法和sorted功能允許您提供自定義的函數來提取用於比較的關鍵:

>>> ls = ['Q1.3', 'Q6.1', 'Q1.2'] 
>>> sorted(ls, key=lambda x: float(x[1:])) 
['Q1.2', 'Q1.3', 'Q6.1'] 
+0

這適用於一般列表,我對它很熟悉。我如何將它應用於熊貓DataFrame? – pythOnometrist

+1

不確定,我承認我的答案不是特定於此庫。 – tweet

186

您還可以做更簡潔:

df.sort_index(axis=1)

編輯

確保你持有價值

df = df.sort_index(axis=1)

或做到位

df.sort_index(axis=1, inplace=True)

+2

記住要用'df.sort_index(axis = 1,inplace = True)'''df = df.sort_index(axis = 1)',通過@multigoodverse – GoJian

+5

或修改'df'' – Jakub

+1

這應該是#1 –

16

Tweet's answer可以傳遞給BrenBarn的回答以上

data.reindex_axis(sorted(data.columns, key=lambda x: float(x[1:])), axis=1) 

因此,對於你的榜樣,說:

vals = randint(low=16, high=80, size=25).reshape(5,5) 
cols = ['Q1.3', 'Q6.1', 'Q1.2', 'Q9.1', 'Q10.2'] 
data = DataFrame(vals, columns = cols) 

你得到:

data 

    Q1.3 Q6.1 Q1.2 Q9.1 Q10.2 
0 73  29  63  51  72 
1 61  29  32  68  57 
2 36  49  76  18  37 
3 63  61  51  30  31 
4 36  66  71  24  77 

然後做:導致

data.reindex_axis(sorted(data.columns, key=lambda x: float(x[1:])), axis=1) 

data 


    Q1.2 Q1.3 Q6.1 Q9.1 Q10.2 
0 2  0  1  3  4 
1 7  5  6  8  9 
2 2  0  1  3  4 
3 2  0  1  3  4 
4 2  0  1  3  4 
20

你可以這樣做:

 
df[sorted(df.columns)] 
+1

我得到「'DataFrame'對象不可調用」。版本:熊貓0.14。 – multigoodverse

13

不要忘記給Wes的答案添加「inplace = True」,或將結果設置爲新的DataFrame。

df.sort_index(axis=1, inplace=True) 
3

最快捷的方法是:

df.sort_index(axis=1) 

要知道,這將創建一個新的實例。因此,你需要將結果存儲在一個新的變量:

sortedDf=df.sort_index(axis=1) 
-1
print df.sort_index(by='Frequency',ascending=False) 

,其中由是列的名字,如果你想如果你需要一個任意基於列的

9

數據集進行排序序列,而不是排序的序列,你可以這樣做:

sequence = ['Q1.1','Q1.2','Q1.3',.....'Q6.1',......] 
your_dataframe = your_dataframe.reindex(columns=sequence) 

我在2.7.10測試了它,它對我有用。

5

幾列,你可以把列命令你想要的東西:

#['A', 'B', 'C'] <-this is your columns order 
df = df[['C', 'B', 'A']] 

這個例子顯示了排序和切片列:

d = {'col1':[1, 2, 3], 'col2':[4, 5, 6], 'col3':[7, 8, 9], 'col4':[17, 18, 19]} 
df = pandas.DataFrame(d) 

你得到:

col1 col2 col3 col4 
1  4  7 17 
2  5  8 18 
3  6  9 19 

然後做:

df = df[['col3', 'col2', 'col1']] 

,導致:

col3 col2 col1 
7  4  1 
8  5  2 
9  6  3  
0

一個用例是,你命名的(一些)你列了一些前綴,並且要與那些前綴排序的所有在一起的列和一些特定的順序(不按字母順序)。例如,您可能會使用Ft_開始您的所有功能,使用Lbl_等的標籤,並且首先需要所有無前綴的列,然後是所有功能,然後是標籤。你可以用下面的函數做到這一點(我會用sum減少列表注意可能的效率問題,但除非你有列了很多,我不,這不是一個問題):

def sortedcols(df, groups = ['Ft_', 'Lbl_']): 
    return df[ sum([list(filter(re.compile(r).search, list(df.columns).copy())) for r in (lambda l: ['^(?!(%s))' % '|'.join(l)] + ['^%s' % i for i in l ])(groups) ], []) ]