【问题标题】:Pandas, stack some columns, unstack some others熊猫,堆叠一些列,取消堆叠一些其他的
【发布时间】:2019-03-26 05:32:35
【问题描述】:

Pandas 整理数据,从一列传播变量,从另一列收集

我的问题

我需要将下面的数据框转换为tidy 格式,其中每一行将是唯一的['GEOG_CODE','COUNTRY'] - 'YEAR' 配对,并且有两个变量,由Group1 定义。

使用 Hadley Wickham 的符号表示 tidy data

  • 观察由位置-时间配对定义。
  • 变量Group1列定义
  • 当前存储在 ['2016' '2017' '2018'] 列中的不同年份。

在 R 中我想:

对于我的问题:

  • 位置['GEOG_CODE','COUNTRY']定义。
  • ['2016' '2017' '2018']列中定义。
  • 变量Group1 == AGroup1 == B定义。

我想将每一行作为位置-时间对,有两个变量。一张给Group1 = A,一张给Group1 = B

我有这个

toy_data = {
    'GEOG_CODE':['123','234','567','901'],
    'COUNTRY':['England' for _ in range(4)],
    'Group1':['A','A','B','B'],
    '2016':np.arange(0,4),
    '2017':np.arange(0,4),
    '2018':np.arange(0,4),
}
in_df = pd.DataFrame(toy_data)
in_df

Out[]:
GEOG_CODE  COUNTRY Group1  2016  2017  2018
0       123  England      A     0     0     0
1       234  England      A     1     1     1
2       567  England      B     2     2     2
3       901  England      B     3     3     3

我想要这个

所以我希望输出看起来像下面的数据框,其中包含 'Group1' 中每个值的列

outcome_data = {
    'GEOG_CODE': np.tile(['123','234','567','901'],3),
    'COUNTRY':['England' for _ in range(4*3)],
    'year':np.tile([2016,2017,2018],4),
    'low_A':np.tile(np.arange(0,4),3),
    'low_B':np.tile(np.arange(0,4),3),
}

out = pd.DataFrame(outcome_data)
out

Out[]:
GEOG_CODE  COUNTRY  year  low_A  low_B
0        123  England  2016      0      0
1        234  England  2017      1      1
2        567  England  2018      2      2
3        901  England  2016      3      3
4        123  England  2017      0      0
5        234  England  2018      1      1
6        567  England  2016      2      2
7        901  England  2017      3      3
8        123  England  2018      0      0
9        234  England  2016      1      1
10       567  England  2017      2      2
11       901  England  2018      3      3

我试过df.melt()

我设法通过使用融化功能获得了一半的数据,但是我不知道如何将组变成行。

id_vars = ['GEOG_CODE', 'COUNTRY', 'Group1']
value_vars = ['2016', '2017', '2018']
var_name = 'Year'
value_name = 'low_Value'

melt = in_df.melt(id_vars=id_vars,value_vars=value_vars,var_name=var_name, value_name=value_name)
melt

Out[]:
GEOG_CODE  COUNTRY Group1  Year  low_Value
0        123  England      A  2016          0
1        234  England      A  2016          1
2        567  England      B  2016          2
3        901  England      B  2016          3
4        123  England      A  2017          0
5        234  England      A  2017          1
6        567  England      B  2017          2
7        901  England      B  2017          3
8        123  England      A  2018          0
9        234  England      A  2018          1
10       567  England      B  2018          2
11       901  England      B  2018          3

【问题讨论】:

  • 你看过pd.wide_to_long函数吗?
  • 是的,但我看不出这对我有何直接帮助,因为 stubnames 的值不是列,它们是列中的值 Group1
  • 为什么会有“low_C”,它是从哪里来的?
  • @TommyLees 如果下面的答案不是您想要的,请告诉我。谢谢!
  • 你是 100% 的天才。谢谢你昨晚也编辑了我的标题

标签: python python-3.x pandas


【解决方案1】:

也许您正在寻找stack 而不是melt

(df.set_index(['GEOG_CODE', 'COUNTRY', 'Group1'])
   .stack()
   .unstack(-2)
   .ffill(axis=1)
   .bfill(axis=1, downcast='infer')
   .add_prefix('low_')
   .reset_index()
   .rename({'level_2': 'year'}, axis=1))

Group1 GEOG_CODE  COUNTRY  year  low_A  low_B
0            123  England  2016      0      0
1            123  England  2017      0      0
2            123  England  2018      0      0
3            234  England  2016      1      1
4            234  England  2017      1      1
5            234  England  2018      1      1
6            567  England  2016      2      2
7            567  England  2017      2      2
8            567  England  2018      2      2
9            901  England  2016      3      3
10           901  England  2017      3      3
11           901  England  2018      3      3

【讨论】:

  • 你能帮我解释一下不同的行的作用吗?不幸的是,代码不能一次删除一行,因为:ValueError: Index contains duplicate entries, cannot reshape.
  • @TommyLees 这在假设每个['GEOG_CODE', 'COUNTRY', 'Group1'] 组合都是唯一的情况下起作用。这个想法是堆叠所有列,同时取消堆叠“Group1”。也许你可以在运行之前尝试df = df.drop_duplicates(subset=['GEOG_CODE', 'COUNTRY', 'Group1'])
  • 如果我把它变成一个带有函数文档字符串的函数,我可以把它添加到你的答案中吗?我很高兴作为新答案发布,但不想接受任何功劳。我只是认为它可能对想要做类似事情的其他人(以及未来的我)有用。
  • @TommyLees 当然,请随时在我的答案底部提出修改建议,我会批准。
  • 我仍然无法让代码处理真正的问题。我确实有非唯一组合的问题。因为['COUNTRY','AREA CODE'] 在多个时间步长上有多个Group1 值。我可以编辑问题还是应该问一个新问题?
猜你喜欢
  • 2019-01-08
  • 2021-12-05
  • 2020-07-11
  • 1970-01-01
  • 1970-01-01
  • 2016-01-08
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多