【问题标题】:R How to modify entries in a dataframe based on 2 conditionsR如何根据2个条件修改数据框中的条目
【发布时间】:2020-04-29 21:44:44
【问题描述】:

使用 R 清理一些杂乱的数据。 假设我有一个数据框 df:

配料 面包 PB 果酱 1“面包、铅、果酱” 2“铅,果酱”x 3“面包”x 4“面包”x ...

我将如何设置一个可以执行以下操作的条件:
如果对应的 (Bread, PB, Jam) 列有 x、 且没有像“Bread,Bread”这样的冗余条目,则修改成分列中的条目

所以清理后的成分列将显示为:

原料: “面包,铅,果酱” “面包,铅,果酱” “面包” “面包,果酱”

非常感谢!

【问题讨论】:

  • 如果您使用dput功能在这里发布一些数据,会很有帮助。
  • 谢谢吉姆。我不知道那是协议。

标签: r data-cleaning


【解决方案1】:

根据您的描述,这是一个基本的 R 解决方案

df$Ingredients <- apply(df,1, function(v) {
  if (sum(v[-1]=="x")>0) {
    u <- unique(c(names(v[-1])[which(v[-1]=="x")],unlist(strsplit(v[1],","))))
    paste0(na.omit(u[match(names(v[-1]),u)]),collapse = ",")
  } else {
    v[1]
  }
}
)

这样

> df
   Ingredients Bread PB Jam
1 Bread,PB,Jam     o  o   o
2 Bread,Jam,PB     x  o   o
3        Bread     x  o   o
4    Bread,Jam     o  o   x

数据

df <- structure(list(Ingredients = c("Bread,PB,Jam", "PB,Jam", "Bread", 
"Bread"), Bread = c("o", "x", "x", "o"), PB = c("o", "o", "o", 
"o"), Jam = c("o", "o", "o", "x")), class = "data.frame", row.names = c(NA, 
-4L))

【讨论】:

  • 谢谢托马斯。之前没用过unique功能。
【解决方案2】:

我们可以将逗号分隔的Ingredients分隔成不同的行,得到所有长格式的列值,group_by每个rowpasteunique值以排序的方式。

library(dplyr)
library(tidyr)

df %>%
  mutate(row = row_number()) %>%
  #mutate_all(~na_if(., "")) %>% #Use this if you have blank values instead of NA
  separate_rows(Ingredients, sep = ",") %>%
  pivot_longer(cols = -row, values_drop_na = TRUE) %>%
  mutate(value = ifelse(value == 'x', name, value)) %>%
  group_by(row) %>%
  summarise(Ingredients = toString(sort(unique(value)))) %>%
  select(-row)

# A tibble: 4 x 1
#  Ingredients   
#  <chr>         
#1 Bread, PB, Jam
#2 Bread, PB, Jam
#3 Bread         
#4 Bread, Jam    

数据

df <- structure(list(Ingredients = structure(c(2L, 3L, 1L, 1L), .Label = c("Bread", 
"Bread,PB,Jam", "PB,Jam"), class = "factor"), Bread = structure(c(NA, 
1L, 1L, NA), .Label = "x", class = "factor"), PB = c(NA, NA, 
NA, NA), Jam = structure(c(NA, NA, NA, 1L), .Label = "x", class = 
"factor")), class = "data.frame", row.names = c("1", "2", "3", "4"))

【讨论】:

    猜你喜欢
    • 2017-11-13
    • 2023-02-02
    • 2022-09-23
    • 1970-01-01
    • 2017-12-30
    • 1970-01-01
    • 2019-07-27
    • 2022-07-18
    • 1970-01-01
    相关资源
    最近更新 更多