Pythonパンダ:選択した列をシリーズではなくDataFrameとして保持する


99

(例えばパンダデータフレームからの単一の列を選択する場合df.iloc[:, 0]df['A']またはdf.A、等)、得られたベクターは、自動的にシリーズの代わりに、単一列のデータフレームに変換されます。ただし、入力引数としてDataFrameを受け取る関数をいくつか作成しています。したがって、関数がdf.columnsにアクセス可能であると想定できるように、Seriesではなく単一列のDataFrameを処理することを好みます。今のところ、のようなものを使用して、シリーズをデータフレームに明示的に変換する必要がありpd.DataFrame(df.iloc[:, 0])ます。これは最もクリーンな方法ではないようです。結果がSeriesではなく単一列のDataFrameになるように、DataFrameから直接インデックスを作成するより洗練された方法はありますか?


6
df.iloc [:、[0]]またはdf [['A']]; ただし、df.Aはシリーズのみを返します
Jeff

回答:


104

@Jeffが言及しているように、これを行うにはいくつかの方法がありますが、loc / ilocを使用してより明確にすることをお勧めします(あいまいなことをしようとすると、エラーを早期に発生させます)。

In [10]: df = pd.DataFrame([[1, 2], [3, 4]], columns=['A', 'B'])

In [11]: df
Out[11]:
   A  B
0  1  2
1  3  4

In [12]: df[['A']]

In [13]: df[[0]]

In [14]: df.loc[:, ['A']]

In [15]: df.iloc[:, [0]]

Out[12-15]:  # they all return the same thing:
   A
0  1
1  3

後者の2つの選択肢は、整数列名の場合のあいまいさを取り除きます(正確には、loc / ilocが作成された理由)。例えば:

In [16]: df = pd.DataFrame([[1, 2], [3, 4]], columns=['A', 0])

In [17]: df
Out[17]:
   A  0
0  1  2
1  3  4

In [18]: df[[0]]  # ambiguous
Out[18]:
   A
0  1
1  3

2
ご迷惑をおかけして申し訳ありませんが、これについては本当に簡単な質問です。エクストラ[]が結果をのDataFrame代わりにどのように作成するかはわかりますSeriesが、パンダのドキュメントのどこでこの種のインデックス構文が説明されていますか?本当に理解できるように、このインデックス作成手法の「正式な」名前を取得しようとしています。THX!
sparc_spread 2017年

3
@sparc_spread pandas.pydata.org/pandas-docs/stable/indexing.html#basics "列のリストを[]に渡して、この順序で列を選択できます。" これに名前があるかどうかわかりません!
アンディ・ヘイデン

ええ、ないようですが、これからも使い続けていきます。APIとドキュメントの両方にどれだけ多くのものが埋め込まれているのか驚くべきことです。THX!
sparc_spread 2017年

Seriesでは利用できなかったデータに対してDataFrameメソッドを使用できるように、単一列のDataFrameが必要な場合があるため、この区別は私にとって便利です。(ISTRプロットメソッドの動作は異なります)。単一要素のリストを使用できることに気付いたとき、それは私にとってひらめきでした!
rufusVS 2018年

4

アンディ・ヘイデンは、インデックスに.iloc / .LOCを活用し、推奨しています(シングルカラム処理)データフレームを移動するための方法です。もう1つの注意点は、インデックス位置の表現方法です。リストされたインデックスラベル/位置を使用し、引数値を指定し、データフレームとしてインデックスアウトします。そうしないと、「pandas.core.series.Series」が返されます。

入力:

    A_1 = train_data.loc[:,'Fraudster']
    print('A_1 is of type', type(A_1))
    A_2 = train_data.loc[:, ['Fraudster']]
    print('A_2 is of type', type(A_2))
    A_3 = train_data.iloc[:,12]
    print('A_3 is of type', type(A_3))
    A_4 = train_data.iloc[:,[12]]
    print('A_4 is of type', type(A_4))

出力:

    A_1 is of type <class 'pandas.core.series.Series'>
    A_2 is of type <class 'pandas.core.frame.DataFrame'>
    A_3 is of type <class 'pandas.core.series.Series'>
    A_4 is of type <class 'pandas.core.frame.DataFrame'>

2

を使用できますdf.iloc[:, 0:1]。この場合、結果のベクトルはDataFrameシリーズではなくaになります。

ご覧のように:

ここに画像の説明を入力してください


1

これらの3つのアプローチが言及されています:

pd.DataFrame(df.loc[:, 'A'])  # Approach of the original post
df.loc[:,[['A']]              # Approach 2 (note: use iloc for positional indexing)
df[['A']]                     # Approach 3

pd.Series.to_frame()は別のアプローチです。

これは方法であるため、上記の2番目と3番目のアプローチが適用されない状況で使用できます。特に、データフレームの列に何らかのメソッドを適用し、出力をシリーズではなくデータフレームに変換する場合に便利です。たとえば、Jupyter Notebookでは、シリーズはきれいに出力されませんが、データフレームは出力されます。

# Basic use case: 
df['A'].to_frame()

# Use case 2 (this will give you pretty output in a Jupyter Notebook): 
df['A'].describe().to_frame()

# Use case 3: 
df['A'].str.strip().to_frame()

# Use case 4: 
def some_function(num): 
    ...

df['A'].apply(some_function).to_frame()
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.