【问题标题】:Calculating pandas DataFrame column which is equal to the missing words from one set to another in a previous DataFrame column计算 pandas DataFrame 列,该列等于前一个 DataFrame 列中从一组到另一组的缺失词
【发布时间】:2019-08-19 12:02:13
【问题描述】:

我需要一些技巧来进行计算。

我的数据框如下所示:

text_id     name     date                words
1           John     2018-01-01          {ocean, blue}
1           John     2018-02-01          {ocean, green} 
2           Anne     2018-03-01          {table, chair}
3           Anne     2018-03-01          {hot, cold, warm}
3           Mark     2018-04-01          {hot, cold}
3           Ethan    2018-05-01          {warm, icy}
4           Paul     2018-01-01          {cat, dog, puppy}
4           John     2018-02-01          {cat}
5           Paul     2018-03-01          {cat, sheep, deer}

在文本中,text_id 代表特定文本(SAME TEXT_ID = SAME TEXT)。 name 列代表编辑文本的人。 date 列代表用户进行编辑的日期。 words 列由用户编辑后形成文本的单词组成。

words 列是一个集合。我需要添加一个附加列erased_words,其中包含THE SAME 文本上当前编辑(在当前行中)和前一个编辑(在上一行中)的设置差异。这可能意味着操作必须通过text_id进行分组。

此处的示例输出为:

text_id     name     date          words            erased_words
1           John     2018-01-01    {ocean,blue}     {}
1           John     2018-02-01    {ocean,green}    {blue}
2           Anne     2018-03-01    {table,chair}    {}
3           Anne     2018-03-01    {hot,cold,warm}  {}
3           Mark     2018-04-01    {hot,cold}       {warm}
3           Ethan    2018-05-01    {warm,icy}       {hot, cold}
4           Paul     2018-01-01    {cat,dog,puppy}  {}
4           John     2018-02-01    {cat}            {dog, puppy}
5           Paul     2018-03-01    {cat,sheep,deer} {}

请注意,基本上,erased_words 列包含i-1 行中的单词列和i 行中的单词列之间的集合差异,仅当第 i 行和第 i-1 行中的 text_id 为一样的,因为:我只希望同一文本中连续版本之间缺少的单词(相同的text_id),而不是不同的单词。

这方面的任何提示都会非常有帮助。

编辑

为了将words 列变成一个集合,请执行以下操作:

df['words'] = df['words'].str.strip('{}').str.split(',').apply(set)

注意:

这不是一个重复的问题,我做了一个类似的问题,但请注意,我想做的计算完全是另一个问题。

请,我仍然没有得到正确的答案。非常感谢任何帮助

【问题讨论】:

  • 您能否提供代码来重新创建您提供的数据框示例?需要始终复制和打印表格,删除空格并添加引号和所有内容

标签: python pandas set difference


【解决方案1】:

出于问题的目的,我假设您的 text_id 列不是您的数据框的索引,但即使它是然后在执行以下操作之前调用 reset_index()

df = pd.DataFrame({"text_id": [1, 1, 2],
                  "name": ["John", "John", "Anne"],
                  "date": ["2018-01-01", "2018-02-01", "2018-03-01"],
                  "words": [{"ocean", "blue"}, {"ocean", "green"}, {"table", "chair"}]})

df["word history 1"] = df["words"].shift(1).fillna(pd.Series([set()]))
df["erased words"] = df["word history 1"] - df["words"]

idx = df.groupby("text_id").head(1).index
df.loc[idx, "erased words"] = df.loc[idx, "erased words"].apply(lambda x: set())
df.drop("word history 1", axis=1, inplace=True)

因此,本质上,我创建了一个 history 列,该列对于原始 words 列中的每一行的延迟为 1。你最终会得到:

df
    text_id  name   date        words           erased words
0   1        John   2018-01-01  {blue, ocean}   {}
1   1        John   2018-02-01  {green, ocean}  {blue}
2   2        Anne   2018-03-01  {chair, table}  {}

【讨论】:

  • @HRDSL 创建额外的word history 1 列?就效率而言,这不应该造成那么大的问题。您的数据集有多大?
  • 我将它用于不同的数据集,但最大的可能有超过 1000000 行和 9 列。
  • @HRDSL 查看在最大数据集上运行需要多长时间。但是,我认为在效率方面没有太多可以改进的地方。
  • 我需要计算 erased_words 集的大小。当我这样做时:df['number_erased_words] = df['erased_words'].apply(len),它返回此错误:'float' 类型的对象没有 len()。有没有办法解决这个问题?
  • 好的,现在erased_words 列中必须有一些Nan 值。我在上面稍微编辑了我的解决方案 - 尝试查看用于创建 df["word history 1"] 的新 df["words"].shift(1).fillna(pd.Series([set()])) 行是否有帮助。如果没有,请在应用 len 函数之前执行 df['erased words'].fillna(pd.Series([set()]), inplace=True)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2020-02-11
  • 2021-05-02
  • 2014-06-12
  • 1970-01-01
  • 2015-12-05
  • 1970-01-01
  • 2019-10-15
相关资源
最近更新 更多