Python Pandas,转换数据帧

时间:2015-06-11 15:05:02

标签: python pandas

我有以下数据框(sim_2005):

Date         ELEM1 ELEM2 ... ELEM1133
2005-01-01   0.021 2.455 ... 345.2
2005-01-02   0.321 2.331 ... 355.1
...          ...   ...   ... ...
2005-12-31   0.789 3.456 ... 459.9
[365 rows x 1133 columns]

我需要使用以下格式将其导入(postgresql)数据库:

ID     Date        ELEM     Value
1      2005-01-01  ELEM1    0.021
2      2005-01-02  ELEM1    0.321
...
366    2005-01-01  ELEM2    2.455
367    2005-01-02  ELEM2    2.331
...
402983 2005-01-01  ELEM1133 345.2
402984 2005-01-02  ELEM1133 355.1
...
403348 2005-12-31  ELEM1133 459.9

我正在尽力迭代列并逐步连接它,

for column in sim_2005:
    sim_concat = pd.concat([pd.DataFrame(sim_2005.columns.values), sim_2005.ix[:, column]], ignore_index=True)

到目前为止还没有产生我正在寻找的东西。

我也试过pandas pivot function,groupby等...但我想我对pandas和python的理解一般不足以进行这种转换。有什么帮助吗?

修改

谢谢,pd.melt就是答案!

 sim_2005_melted = pd.melt(sim_2005, id_vars=sim_2005.index.name, value_vars=list(sim_2005.columns.values), var_name='ELEM', value_name='Q_sim').sort(columns='Date')

结果:

ID     Date   ELEM     Q_sim
1      NaN    ELEM1    0.021
2      NaN    ELEM1    0.321
...
366    NaN    ELEM2    2.455
367    NaN    ELEM2    2.331
...
402983 NaN    ELEM1133 345.2
402984 NaN    ELEM1133 355.1

由于某种原因,日期时间索引没有被转移,但整体结构正是我想要的!

1 个答案:

答案 0 :(得分:1)

看起来你正在用pandas术语进行“从宽到窄”的转换。一种方法是使用melt

在这种情况下,您可以执行以下操作:

pd.melt(df, id_vars=['Date'], value_vars=['ELEM1', 'ELEM2']).sort(columns='Date')

表示具有两个“宽”列['ELEM1', 'ELEM2']的数据框。对于示例中的~1K列,您显然不是手动编写它们,而是使用某种列表理解来创建value_vars

示例

df = pd.DataFrame({
    'Date': range(4),
    'ELEM1': range(1, 5),
    'ELEM2': range(11, 15),
    'ELEM2': range(-5, -1)
})

>> df
    Date    ELEM1   ELEM2
0   0   1   -5
1   1   2   -4
2   2   3   -3
3   3   4   -2

>> pd.melt(df, id_vars=['Date'], value_vars=['ELEM1', 'ELEM2']).sort(columns='Date')
    Date    variable    value
0   0   ELEM1   1
4   0   ELEM2   -5
1   1   ELEM1   2
5   1   ELEM2   -4
2   2   ELEM1   3
6   2   ELEM2   -3
3   3   ELEM1   4
7   3   ELEM2   -2