我在Python中使用Pandas编写了以下代码:

all_data = {}
for ticker in ['FIUIX', 'FSAIX', 'FSAVX', 'FSTMX']:
    all_data[ticker] = web.get_data_yahoo(ticker, '1/1/2010', '1/1/2015')

prices = DataFrame({tic: data['Adj Close'] for tic, data in all_data.iteritems()})  
returns = prices.pct_change()

我知道我可以像这样进行回归:

regs = sm.OLS(returns.FIUIX,returns.FSTMX).fit()

但是我如何为数据框架中的每一列做到这一点呢?具体来说,我如何遍历列,以便在每个列上运行回归?

具体来说,我想在FSTMX上回归彼此的股票代码(FIUIX, FSAIX和FSAVX),并存储每次回归的残差。

我尝试过以下几种方法,但没有一种能达到预期的效果:

resids = {}
for k in returns.keys():
    reg = sm.OLS(returns[k],returns.FSTMX).fit()
    resids[k] = reg.resid

代码的返回[k]部分有问题吗?如何使用k值访问列?或者还有更简单的方法吗?


当前回答

我有点晚了,但我是这么做的。的步骤:

创建所有列的列表 使用itertools获取x的组合 将每个结果R平方值与排除列列表一起附加到结果数据框架中 将结果DF按R平方的降序排序,看看哪个是最合适的。

这是我在DataFrame上使用的代码,称为aft_tmt。请随意推断您的用例。

import pandas as pd
# setting options to print without truncating output
pd.set_option('display.max_columns', None)
pd.set_option('display.max_colwidth', None)

import statsmodels.formula.api as smf
import itertools

# This section gets the column names of the DF and removes some columns which I don't want to use as predictors.
itercols = aft_tmt.columns.tolist()
itercols.remove("sc97")
itercols.remove("sc")
itercols.remove("grc")
itercols.remove("grc97")
print itercols
len(itercols)

# results DF
regression_res = pd.DataFrame(columns = ["Rsq", "predictors", "excluded"])

# excluded cols
exc = []

# change 9 to the number of columns you want to combine from N columns.
#Possibly run an outer loop from 0 to N/2?
for x in itertools.combinations(itercols, 9):
    lmstr = "+".join(x)
    m = smf.ols(formula = "sc ~ " + lmstr, data = aft_tmt)
    f = m.fit()
    exc = [item for item in x if item not in itercols]
    regression_res = regression_res.append(pd.DataFrame([[f.rsquared, lmstr, "+".join([y for y in itercols if y not in list(x)])]], columns = ["Rsq", "predictors", "excluded"]))

regression_res.sort_values(by="Rsq", ascending = False)

其他回答

你可以使用ix根据数据帧列的位置建立索引。

df1.ix[:,1]

例如,这将返回第一列。(0是索引)

df1.ix[0,]

这将返回第一行。

df1.ix[:,1]

这将是第0行和第1列的交点:

df1.ix[0,1]

等等。因此,您可以enumerate() returns.keys():并使用该数字来索引数据帧。

一种解决方法是转置DataFrame并遍历各行。

for column_name, column in df.transpose().iterrows():
    print column_name

我遇到这个问题是因为我正在寻找一个只包含列的干净迭代器(Series,没有名称)。

除非我弄错了,没有这样的事情,如果这是真的,有点烦人。特别是,人们有时想要为变量分配几个单独的列(Series),例如:

x, y = df[['x', 'y']]  # does not work

有一个接近的df.items(),但它给出了一个元组迭代器(column_name, column_series)。有趣的是,有一个对应的df.keys()返回df.keys()。列,即列名作为索引,因此a, b= df[['x', 'y']].keys()正确分配a='x'和b='y'。但是没有对应的df.values(),因为df.values是df.values()Values是一个属性,返回底层numpy数组。

一种(不优雅的)方法是:

x, y = (v for _, v in df[['x', 'y']].items())

但没有我想的那么复杂。

根据已接受的答案,如果还需要与每列对应的索引:

for i, column in enumerate(df):
    print i, df[column]

上面的df[column]类型是Series,它可以简单地转换为numpy ndarray:

for i, column in enumerate(df):
    print i, np.asarray(df[column])

我有点晚了,但我是这么做的。的步骤:

创建所有列的列表 使用itertools获取x的组合 将每个结果R平方值与排除列列表一起附加到结果数据框架中 将结果DF按R平方的降序排序,看看哪个是最合适的。

这是我在DataFrame上使用的代码,称为aft_tmt。请随意推断您的用例。

import pandas as pd
# setting options to print without truncating output
pd.set_option('display.max_columns', None)
pd.set_option('display.max_colwidth', None)

import statsmodels.formula.api as smf
import itertools

# This section gets the column names of the DF and removes some columns which I don't want to use as predictors.
itercols = aft_tmt.columns.tolist()
itercols.remove("sc97")
itercols.remove("sc")
itercols.remove("grc")
itercols.remove("grc97")
print itercols
len(itercols)

# results DF
regression_res = pd.DataFrame(columns = ["Rsq", "predictors", "excluded"])

# excluded cols
exc = []

# change 9 to the number of columns you want to combine from N columns.
#Possibly run an outer loop from 0 to N/2?
for x in itertools.combinations(itercols, 9):
    lmstr = "+".join(x)
    m = smf.ols(formula = "sc ~ " + lmstr, data = aft_tmt)
    f = m.fit()
    exc = [item for item in x if item not in itercols]
    regression_res = regression_res.append(pd.DataFrame([[f.rsquared, lmstr, "+".join([y for y in itercols if y not in list(x)])]], columns = ["Rsq", "predictors", "excluded"]))

regression_res.sort_values(by="Rsq", ascending = False)