首页 > 解决方案 > 有条件地更新列中信息的更好方法

问题描述

我在一年的时间里定期收集信息。第一个收集点“t1”充当一种参考水平。

总体而言,如果返回的“值”为 4 或更高,则“颜色”列条目应为“红色”。如果小于 4,它将读取为“绿色”。

现在,如果在后续数据收集点期间,变量的值比“t1”处记录的值大 2 个或更多点,那么我想将颜色列条目更新为“蓝色”。

请参阅下面的示例...

data <- tibble::tribble(
 ~parent, ~variable, ~value, ~colour,
    "t1",   "happy",     4L,   "red",
    "t2",   "happy",     5L,   "red",
    "t3",   "happy",     3L, "green",
    "t1",     "sad",     1L, "green",
    "t2",     "sad",     3L, "green",
    "t3",     "sad",     3L, "green"
 )

time <- c('t2', 't3')
my_vars <- c('happy', 'sad')

for (i in time) {
 for (x in my_vars){
   if (data$value[data$parent == i & data$variable == x] >= 
       data$value[data$parent == 't1' & data$variable == x] + 2) {
     data$colour[data$parent == i & data$variable == x] <- 'blue'
   } else {
     data$colour[data$parent == i & data$variable == x] <- data$colour[data$parent == i & data$variable == x]
   }
 }
}

这给出了...的输出 桌子

问:我正在寻找一种更优雅的方式来实现这一点,因为我使用的数据集具有更长的列名,而且代码难以阅读,而且只是跑出我的屏幕。我更喜欢使用一些dplyr函数来做这件事,但最初的尝试失败了,我回到了上面更熟悉的代码结构。

此外,在现实和现实世界的数据中,我将有大约 20 多个变量。我需要防止存在抛出代码的 NA(例如,如果 t1 值是 NA,它会抛出错误)并且我不确定如何处理这种情况,因为我不熟悉它来还没有建立检查,因此在这方面的任何指示都会受到极大的欢迎。

谢谢。

标签: rdplyrtidyverse

解决方案


对于每个variable,您可以将值与 进行比较ifelse

library(dplyr)  

data %>%
  group_by(variable) %>%
  mutate(colour = ifelse(value - value[match('t1', parent)] >= 2, 'blue', colour)) %>%
  ungroup

#  parent variable value colour
#  <chr>  <chr>    <int> <chr> 
#1 t1     happy        4 red   
#2 t2     happy        5 red   
#3 t3     happy        3 green 
#4 t1     sad          1 green 
#5 t2     sad          3 blue  
#6 t3     sad          3 blue  

推荐阅读