这个问题似乎很简单,可以说是近乎愚蠢。但考虑到我的场景,我似乎必须这样做,以保持跨多个数据帧的一系列计算的效率。
脚本:
我有一堆pandas数据帧,其中列名由名称部分和时间部分构成,例如
'AA_2018'
'BB_2017'
. 我对不同数据帧的不同列进行计算,所以我必须过滤掉时间段。作为一个
mcve
我想把包含
'AA'
从包含
'BB'
并忽略此数据帧中的所有其他列:
import pandas as pd
import numpy as np
dates = pd.date_range('20180101',periods=3)
df = pd.DataFrame(np.random.randn(3,3),index=dates,columns=['AA_2018', 'AB_2018', 'BB_2017'])
diff_series = df['AA_2018'] - df['BB_2017']
这将返回一个熊猫系列,因为我使用单括号
[]
如果我用了双括号的话,那就不是datframe了
[[]]
.
我的挑战:
diff_series
pandas.core.series.Series
. 但既然我有一些过滤工作要做,我就用
df.filter()
返回一个包含一列和
不
a系列:
# in:
colAA = df.filter(like = 'AA')
# out:
# AA_2018
# 2018-01-01 0.801295
# 2018-01-02 0.860808
# 2018-01-03 -0.728886
# in:
# type(colAA)
# out:
# pandas.core.frame.DataFrame
Snce公司
colAA
属于类型
pandas.core.frame.DataFrame
,下面也返回一个数据帧:
# in:
colAA = df.filter(like = 'AA')
colBB = df.filter(like = 'BB')
df_filtered = colBB - colAA
# out:
AA_2018 BB_2017
2018-01-01 NaN NaN
2018-01-02 NaN NaN
2018-01-03 NaN NaN
这不是我想要的。这是:
# in:
diff_series = df['AA_2018'] - df['BB_2017']
# out:
2018-01-01 0.828895
2018-01-02 -1.153436
2018-01-03 -1.159985
为什么我要这么做?
因为我想用
.to_frame()
使用基于我使用的过滤器的指定名称。
我认为低效的方法是:
# in:
colAA_values = [item for sublist in colAA.values for item in sublist]
# (because colAA.values returns a list of lists)
colBB_values = [item for sublist in colBB.values for item in sublist]
serAA = pd.Series(colAA_values, colAA.index)
serBB = pd.Series(colBB_values, colBB.index)
df_diff = (serBB - serAA).to_frame(name = 'someFilter')
# out:
someFilter
2018-01-01 -0.828895
2018-01-02 1.153436
2018-01-03 1.159985
我尝试的/我希望的工作:
# in:
(df.filter(like = 'BB') - df.filter(like = 'AA')).to_frame(name = 'somefilter')
# out:
# AttributeError: 'DataFrame' object has no attribute 'to_frame'
# (Of course because df.filter() returns a one-column dataframe)
df.filter()
可能会退回熊猫系列,但不会。
我想我可以问这样的问题:
How to convert pandas dataframe column to a pandas series?
但这似乎也没有一个高效的内置单行线。大多数搜索结果的处理方式相反。我已经花了相当长的时间来处理潜在的解决方案,一个显而易见的解决方案可能就在眼前,但我希望你们中的一些人能就如何有效地做到这一点提出建议。
import pandas as pd
import numpy as np
dates = pd.date_range('20180101',periods=3)
df = pd.DataFrame(np.random.randn(3,3),index=dates,columns=['AA_2018', 'AB_2018', 'BB_2017'])
#diff_series = df[['AA_2018']] - df[['BB_2017']]
#type(diff_series)
colAA = df.filter(like = 'AA')
colBB = df.filter(like = 'BB')
df_filtered = colBB - colAA
#type(df_filtered)
#type(colAA)
#colAA.values
#colAA.values returns a list of lists that has to be flattened for use in pd.Series
colAA_values = [item for sublist in colAA.values for item in sublist]
colBB_values = [item for sublist in colBB.values for item in sublist]
serAA = pd.Series(colAA_values, colAA.index)
serBB = pd.Series(colBB_values, colBB.index)
df_diff = (serBB - serAA).to_frame(name = 'someFilter')
# Attempts:
# (df.filter(like = 'BB') - df.filter(like = 'AA')).to_frame(name = 'somefilter')