2016-02-02 9 views
2

我正在使用Pandas DataFrame來管理某些結果數據。爲了在我的數據框上實現'切片和切塊',我使用'pivot_table'函數。除此之外,爲了獲得列的自定義排序,我將其中一列轉換爲「分類」列。 我發現,當我嘗試和打印數據幀它提供了以下錯誤:使用catagorical列的數據框無法打印

AttributeError的:如果我更改了代碼,以便該列是「範疇」對象有沒有屬性「標誌」

不'分類',那麼它的作品。但是,我的透視結果有默認(按字母順序)的列順序。

這裏是我的代碼砍下版本:

import pandas as pd 

# Build data frame 
data=[ 
    (1, 'ABC', '3M', 0.1), 
    (1, 'ABC', '1Y', 0.1), 
    (1, 'ABC', '2Y', 0.1), 
    (1, 'ABC', '3Y', 0.1), 
    (1, 'ABC', '5Y', 0.1), 
    (1, 'ABC', '7Y', 0.1), 
    (1, 'ABC', '10Y', 0.1), 
    (1, 'ABC', '15Y', 0.1), 
    (1, 'ABC', '20Y', 0.1), 
    (1, 'ABC', '25Y', 0.1), 
    (1, 'ABC', '30Y', 0.1), 
    (2, 'ABC', '3M', 0.1), 
    (2, 'ABC', '1Y', 0.1), 
    (2, 'ABC', '2Y', 0.1), 
    (2, 'ABC', '3Y', 0.1), 
    (2, 'ABC', '5Y', 0.1), 
    (2, 'ABC', '7Y', 0.1), 
    (2, 'ABC', '10Y', 0.1), 
    (2, 'ABC', '15Y', 0.1), 
    (2, 'ABC', '20Y', 0.1), 
    (2, 'ABC', '25Y', 0.1), 
    (2, 'ABC', '30Y', 0.1)] 
df = pd.DataFrame(data=data, columns=('Ord', 'Name', 'label', 'Value')) 

# Obtain a custom sorted list of lables 
label_sort_order = {'3M': 1, '1Y': 2, '2Y': 3, '3Y': 4, '5Y': 5, '7Y': 6, '10Y': 7, '15Y': 8, '20Y': 9, '25Y': 10, '30Y': 11} 
labels = label_sort_order.keys() 
labels = sorted(labels, key=lambda label: label_sort_order[label]) 

# Convert label column to 'Categorical' so when pivoted it will respect the custom column ordering 
df['label'] = pd.Categorical(df['label'], labels) 
df_pivot = pd.pivot_table(df, index=['Name'], columns=['Ord', 'label']) 

print(df_pivot) # Thows exception 

我使用python 3.4.3,並安裝了熊貓0.16.2。

任何人都可以解釋爲什麼會發生這種異常,以及如何避免它?或者,也許有更好的辦法,我想要做的就是控制我旋轉的數據框的列順序。

+0

隨着大熊貓0.17.1你的代碼工作完美無缺。你可以嘗試更新到最新版本? – IanS

+0

它適用於python 2.7和pandas 0.17.1,它可能是您的熊貓版本中的一個錯誤。你能夠更新到最新版本嗎?作爲解決方法,您可以將標籤保留爲字符串或將其轉換爲「期間」。 – Goyo

+0

我更新爲熊貓0.17.1,問題消失。我現在很滿意。非常感謝小費。 –

回答

0

您可以重新排序在任何級別的標籤與reindex功能的多指標:

首先我重用代碼:

df = pd.DataFrame(data=data, columns=('Ord', 'Name', 'label', 'Value')) 
label_sort_order = {'3M': 1, '1Y': 2, '2Y': 3, '3Y': 4, '5Y': 5, '7Y': 6, '10Y': 7, '15Y': 8, '20Y': 9, '25Y': 10, '30Y': 11} 
labels = label_sort_order.keys() 
labels = sorted(labels, key=lambda label: label_sort_order[label]) 

然後我轉以使用reindex功能:

df_pivot.transpose().reindex(labels, level='label') 

更新reindex是在熊貓0.17中新增的。你一定要考慮更新。

+0

我剛剛檢查:'reindex'在熊貓0.17中是新的。它比使用分類列更好:) – IanS

0

可以使用Ordered Categorical創建列label

# Obtain a custom sorted list of lables 
label_sort_order = {'3M': 1, '1Y': 2, '2Y': 3, '3Y': 4, '5Y': 5, '7Y': 6, '10Y': 7, '15Y': 8, '20Y': 9, '25Y': 10, '30Y': 11} 
print label_sort_order 
{'3Y': 4, '5Y': 5, '1Y': 2, '2Y': 3, '3M': 1, '30Y': 11, '15Y': 8, '25Y': 10, '20Y': 9, '10Y': 7, '7Y': 6} 

#swap keys and values in dictionary label_sort_order 
swap_dict = dict((v,k) for k,v in label_sort_order.items()) 
print swap_dict 
{1: '3M', 2: '1Y', 3: '2Y', 4: '3Y', 5: '5Y', 6: '7Y', 7: '10Y', 8: '15Y', 9: '20Y', 10: '25Y', 11: '30Y'} 

#create new Series - is sorted by keys converted to index 
s = pd.Series(swap_dict) 
print s 
1  3M 
2  1Y 
3  2Y 
4  3Y 
5  5Y 
6  7Y 
7  10Y 
8  15Y 
9  20Y 
10 25Y 
11 30Y 
dtype: object 

#get sorted values of Series s 
print s.values 
['3M' '1Y' '2Y' '3Y' '5Y' '7Y' '10Y' '15Y' '20Y' '25Y' '30Y'] 
#add parameter ordered=True 
print pd.Categorical(df['label'], categories=s.values, ordered=True) 
[3M, 1Y, 2Y, 3Y, 5Y, ..., 10Y, 15Y, 20Y, 25Y, 30Y] 
Length: 22 
Categories (11, object): [3M < 1Y < 2Y < 3Y ... 15Y < 20Y < 25Y < 30Y] 
df['label'] = pd.Categorical(df['label'], categories=s.values, ordered=True) 

print pd.pivot_table(df, index=['Name'], columns=['Ord', 'label']) 
     Value            ...     \ 
Ord  1            ...  2    
label 3M 1Y 2Y 3Y 5Y 7Y 10Y 15Y 20Y 25Y ... 1Y 2Y 3Y 
Name              ...     
ABC  0.1 0.1 0.1 0.1 0.1 0.1 0.1 0.1 0.1 0.1 ... 0.1 0.1 0.1 


Ord          
label 5Y 7Y 10Y 15Y 20Y 25Y 30Y 
Name          
ABC 0.1 0.1 0.1 0.1 0.1 0.1 0.1 

[1 rows x 22 columns]