0

我在 Python 和 Pandas 中设置我的第一个分析(两者都是新手),并且有一些关于如何正确设置的问题/问题。

本质上,我正在尝试按时间序列查看用户行为,但我的用户数比天数还多,因此我尝试每月查看一次。我已经建立了DataFrame这种方式:

df2 = pd.DataFrame({'ID':range(100)})
df2['Day1'] = random.sample(xrange(1000), 100)
df2['Day2'] = random.sample(xrange(1000), 100)
df2['Day3'] = random.sample(xrange(1000), 100)

我尝试通过多种方式向“ID”列添加索引,但 1) 不确定我是否需要它,以及 2) 我的任何方法都不会采用。这是我尝试过的:

df2 = pd.DataFrame({'ID':range(100)}, index_col='ID')
df2 = pd.DataFrame({'ID':range(100)}, index_col=0)
df2.index(0)
df2.index('ID')
df2.reindex(index='ID')
df2.reindex(index=0)

我试图创建一个新数据框的最终输出,它将显示第 2 天的值是否比第 1 天小 95%,第 3 天是否比第 2 天小 95% - 以后(假设我有DataFrame100 列)。我看起来的输出可能如下所示:

ID   Day2   Day3
1    NaN    1
2    NaN    NaN
3    NaN    NaN
4    1      NaN

我相信确定这一点的适当方法是运行一个 for 循环,如下所示:

for i in df2:
  if (Day2-Day1)/Day1 < .95:
    print 1

但是,我不确定如何引用函数中的列,也不确定如何使该函数灵活地包含DataFrame. 我应该如何引用这个函数的列?

我应该如何引用这个函数的列?

4

2 回答 2

1

使用面板可能有一种更简单的方法,但我还没有时间序列方面的经验。这就是我将如何使用 DataFrames 完成您想要的:

首先制作一个假人DataFrame

In [231]: df2 = DataFrame(np.random.rand(100,3)*100, columns=['Day1','Day2','Day3'])

In [232]: df2.head()
Out[232]:
        Day1       Day2       Day3
0  93.347819  92.866771  91.381466
1   7.819967  26.415094  79.477087
2  98.792627  92.940538  83.774519
3  64.182073  22.563504  15.631763
4  82.460359  89.743872  87.511540

现在,DataFrame通过删除第一列来创建一个新的df2

In [233]: df3 = df2.ix[:,1:]

In [234]: df3.head()
Out[234]:
        Day2       Day3
0  92.866771  91.381466
1  26.415094  79.477087
2  92.940538  83.774519
3  22.563504  15.631763
4  89.743872  87.511540

ix 表示法允许您对列进行切片。一开始可能会令人困惑,但它在英文中的意思是:“取所有行,只取从 1 到结尾的列”。

此时两者DataFrames具有相同的索引。您不需要创建自己的“ID”,除非您需要它用于其他用途。Pandas 会自动DataFrames为您编制索引。这对齐了DataFrames所有类型的操作。它对列做同样的事情。它将DataFrames按列名排列并执行您想要的任何操作。由于您想除以“下一天”,我们必须更改以下列df3

In [235]: df3.columns = df2.columns[:-1]

In [236]: df3.head()
Out[236]:
        Day1       Day2
0  92.866771  91.381466
1  26.415094  79.477087
2  92.940538  83.774519
3  22.563504  15.631763
4  89.743872  87.511540

现在我们已经重命名了列,所以它们将按照我们想要的方式对齐。执行除法计算很容易,因为 Pandas 将完成所有对齐。无需循环!

In [244]: df4 = (df2/df3 < .95)

In [245]: df4.head()
Out[245]:
    Day1   Day2   Day3
0  False  False  False
1   True   True  False
2  False  False  False
3  False  False  False
4   True  False  False
于 2012-12-26T17:21:58.513 回答
0

由于当前形式的 pandas 假设时间序列数据在索引中按时间排列,而不是按列排列,因此转置 DataFrame 至少暂时可以使用许多内置方法,例如 shift// diff/ pct_changeetc。

In [78]: df = DataFrame(np.random.rand(100, 3) * 100,
                        columns=['Day1', 'Day2', 'Day3'])

In [79]: df.head()
Out[79]: 
        Day1       Day2       Day3
0  27.113276   0.827977  37.059887
1  48.817798  19.335033  12.476411
2  27.001015  18.147742  33.094676
3  38.428321  95.609824  72.395564
4  63.626472  36.207677   1.328216

In [80]: dft = df.T

In [82]: dft.ix[:, :5]
Out[82]: 
              0          1          2          3          4          5
Day1  27.113276  48.817798  27.001015  38.428321  63.626472  25.900132
Day2   0.827977  19.335033  18.147742  95.609824  36.207677   0.191767
Day3  37.059887  12.476411  33.094676  72.395564   1.328216  37.011027

In [89]: dft.pct_change().ix[:, :5]
Out[89]: 
              0         1         2         3         4           5
Day1        NaN       NaN       NaN       NaN       NaN         NaN
Day2  -0.969462 -0.603935 -0.327887  1.488004 -0.430934   -0.992596
Day3  43.759576 -0.354725  0.823625 -0.242802 -0.963317  191.999688

In [94]: chg = (dft.pct_change().dropna() < .95).T.astype(int)

In [95]: chg.head()
Out[95]: 
   Day2  Day3
0     1     0
1     1     1
2     1     1
3     0     1
4     1     1
于 2012-12-29T07:21:22.437 回答