如何将 pandas DataFrame 的列解压为多个变量

How to unpack the columns of a pandas DataFrame to multiple variables

如果维度匹配,列表或 numpy 数组可以解包为多个变量。对于 3xN 数组,以下将起作用:

import numpy as np 
a,b =          [[1,2,3],[4,5,6]]
a,b = np.array([[1,2,3],[4,5,6]])
# result: a=[1,2,3],   b=[4,5,6]

如何实现 pandas DataFrame 的列的类似行为?扩展上面的例子:

import pandas as pd 
df = pd.DataFrame([[1,2,3],[4,5,6]])
df.columns = ['A','B','C']    # Rename cols and
df.index = ['i', 'ii']        # rows for clarity

以下未按预期工作:

a,b = df.T
# result: a='i',   b='ii'
a,b,c = df
# result: a='A',   b='B',   c='C'

但是,我想得到的是:

a,b,c = unpack(df)
result: a=df['A'], b=df['B'], c=df['C']

功能 unpack 是否已在 pandas 中可用?还是可以通过简单的方式模仿?

我只是想出以下效果,这已经接近我尝试实现的目标:

a,b,c = df.T.values        # Common
a,b,c = df.T.to_numpy()    # Recommended
# a,b,c = df.T.as_matrix() # Deprecated

详情: 一如既往,事情比人们想象的要复杂一些。请注意 pd.DataFrame stores columns separately in Series. Calling df.values (or better: df.to_numpy()) is potentially expensive, as it combines the columns in a single ndarray,这可能涉及复制操作和类型转换。此外,生成的容器有一个 dtype 能够容纳数据框中的所有数据。

总而言之,上述方法丢失了每列 dtype 信息并且可能很昂贵。以下列方式之一迭代列在技术上更清洁(有更多选项):

# The following alternatives create VIEWS!
a,b,c = (v for _,v in df.items())      # returns pd.Series
a,b,c = (df[c] for c in df)            # returns pd.Series

请注意,上面的代码创建了 views!修改数据可能会触发 SettingWithCopyWarning.

a.iloc[0] = "blabla"    # raises SettingWithCopyWarning

如果要修改解压缩的变量,则必须复制列。

# The following alternatives create COPIES!
a,b,c = (v.copy() for _,v in df.items())      # returns pd.Series
a,b,c = (df[c].copy() for c in df)            # returns pd.Series
a,b,c = (df[c].to_numpy() for c in df)        # returns np.ndarray

虽然这样更简洁,但需要更多字符。我个人不建议将上述方法用于生产代码。但为了避免打字(例如,在交互式 shell 会话中),它仍然是一个不错的选择...

# More verbose and explicit alternatives
a,b,c = df["the first col"], df["the second col"], df["the third col"]
a,b,c = df.iloc[:,0], df.iloc[:,1], df.iloc[:,2]