【问题标题】:How to create a new dataframe row with a new column for every combination of other two columns?如何为其他两列的每个组合创建一个带有新列的新数据框行?
【发布时间】:2019-08-14 13:05:28
【问题描述】:

我有一个 Pandas 数据框,其中包含两列 id1id2,我需要创建一个新列 - type 值,其中 id1id2 的每个组合来自输入和那些4 个值应为freecallpristatus

输入:

df = pd.DataFrame({'id1':[1,1,2,2],
                   'id2':[1,2,1,2]})

输出:

我试图在 pandas 文档中搜索有关此案例的函数,甚至不知道如何用文字表达。所以我只是觉得在这里解释会更好。

如何创建一个包含 4 种类型值的新列。

@jezrael:

如何将此type 列与现有数据框合并。

我也有其他列,其中包含以下一些值

输入:

输出:

我只想将现有输入行中的值复制到name 列的输出列。而且这样的专栏还有很多。

【问题讨论】:

  • 不要添加图片作为数据,我们不能复制图片。
  • 当我复制粘贴数据时,Stackoverflow 自动建议添加来自 imgur.com 的图片。没有不添加的选项。
  • 你将数据添加到 HTML sn-p
  • 如果您要粘贴的内容是图像数据,Stack Overflow 会提示您上传到 imgur。我们想要文本数据。如果您的 IDE 未将数据显示为文本,您可能需要从命令行运行程序并从那里复制数据。
  • 我是从 excel 表格中复制的,而不是图像。

标签: python pandas csv dataframe multiple-columns


【解决方案1】:

如果需要所有元素的所有组合,请使用 product 与列和列表并通过构造函数创建 DataFrame

from  itertools import product

df = pd.DataFrame({'id1':[1,1,2,2],
                   'id2':[1,2,1,2],
                   'name':['name11','name12','name21','name22']})

L = ['free', 'call', 'pri', 'status']

cols = ['id1','id2', 'name']
L1 = df[cols].values.tolist()

df2 = pd.DataFrame([x + [y] for x, y in (product(L1, L))], columns=cols + ['type'])
print (df2)
    id1  id2    name    type
0     1    1  name11    free
1     1    1  name11    call
2     1    1  name11     pri
3     1    1  name11  status
4     1    2  name12    free
5     1    2  name12    call
6     1    2  name12     pri
7     1    2  name12  status
8     2    1  name21    free
9     2    1  name21    call
10    2    1  name21     pri
11    2    1  name21  status
12    2    2  name22    free
13    2    2  name22    call
14    2    2  name22     pri
15    2    2  name22  status

或者将cross join 与从列表L 创建的DataFrame 一起使用:

cols = ['id1','id2', 'name']
L = ['free', 'call', 'pri', 'status']

df1 = pd.DataFrame({'type':L, 'a':1})

df2 = df[cols].assign(a=1).merge(df1, on='a').drop('a', axis=1)
print (df2)
    id1  id2    name    type
0     1    1  name11    free
1     1    1  name11    call
2     1    1  name11     pri
3     1    1  name11  status
4     1    2  name12    free
5     1    2  name12    call
6     1    2  name12     pri
7     1    2  name12  status
8     2    1  name21    free
9     2    1  name21    call
10    2    1  name21     pri
11    2    1  name21  status
12    2    2  name22    free
13    2    2  name22    call
14    2    2  name22     pri
15    2    2  name22  status

【讨论】:

  • 其实我有这么多专栏。不只是id1id2 发布以简化问题。有没有什么方法可以添加这种类型的列而不会造成太大的混乱?
  • @SukumarRdjf - 当然,使用L1 = df[['id1','id2']].values.tolist()
  • 当我运行第一个选项时,我收到如下错误“NameError: name 'product' is not defined”(使用 pandas 0.25)
  • @jezrael 您能否查看更新后的问题,并让我知道这种情况是否有任何可能。
  • 用 300 万行填充数据集的列,itertools.product 填充了所有 16GB 的 RAM。 pandas cross join 对我来说效果很好。谢谢@jezrael
【解决方案2】:

您还可以使用重复和分配的组合:

df = (df.loc[df.index.repeat(len(df))]
        .assign(v=len(df)*['free', 'call', 'pri', 'status'])
        .reset_index(drop=True))

【讨论】:

    【解决方案3】:

    你可以试试:

    data = list()
    for index, row in df.iterrows():
        for value in ['free', 'call', 'pri', 'status']:
            data.append((row.id1, row.id2, value))
    pd.DataFrame(data, columns=['id1', 'id2', 'type'])
    

    【讨论】:

      【解决方案4】:

      你可以这样做

      id1 = np.array([1,1,2,2]).repeat(4)
      id2 = np.array([1,2,1,2]).repeat(4)
      df = pd.DataFrame({'id1':id1,
                         'id2':id2})
      df["type"] = ["free", "call", "pri", "status"]*4
      print(df)
      

      输出是

          id1  id2    type
      0     1    1    free
      1     1    1    call
      2     1    1     pri
      3     1    1  status
      4     1    2    free
      5     1    2    call
      6     1    2     pri
      7     1    2  status
      8     2    1    free
      9     2    1    call
      10    2    1     pri
      11    2    1  status
      12    2    2    free
      13    2    2    call
      14    2    2     pri
      15    2    2  status
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2018-12-22
        • 1970-01-01
        • 2017-08-15
        • 1970-01-01
        相关资源
        最近更新 更多