dplyr:每组最常见的课程+条件,没有总结

时间:2017-08-26 07:49:40

标签: r count dplyr mutate

我有一个测量某些事件的传感器(2类或更多+它们之间的白噪声)。   我想为我的数据添加一个窗口,并根据事件比例的一些规则对每个窗口进行分类:

  • 如果窗口中的白噪声超过90%=>所有行都必须标记为白噪声
  • 如果白噪声低于90%,则在窗口中标记最多的事件

我找到了一种创建窗口的方法(但如果你有更好的方式我感兴趣的话,它不是很优雅)   我不知道如何应用规则并在初始data.frame中标记行   注意:我不想总结"我的数据,只需在每个窗口添加一个重复的标签。   在示例中,我想要的输出是添加标签" event1"对于所有窗口1& 2观察," event2"用于窗口3,以及"白噪声"对于窗口4等

  df = data.frame(value=c(1,1,1,2,2,1,2,1,3,2,3,6,7,8,4,2,1,1,1,2,1,1,2,1,3,3,1,5,8,9,9,8,
                          1,-4,-5,-7,-9,-3,-2,-1,1,1,1,1,1,2,1,1,1,2,1,1,1,2,2,1,2,3,5,7,7,7,6,2))
  df$class="white.noise"; df$class[df$value<1]<-"event2"; df$class[df$value>2]<-"event1"

  # first create a window 
  window.size=13
  df2 = df %>% mutate('window' = rep(1:100, each=window.size)[1:nrow(df)])

  # compute frequencies per window
  df2 %>% group_by(window, class) %>% tally %>% mutate(n=n/window.size*100)

2 个答案:

答案 0 :(得分:1)

您可以在单独的数据集中汇总每个窗口的相应标记,&amp;加入原来的那个:

df2.sum <- df2 %>%
  group_by(window, class) %>%
  summarise(count = n()) %>%
  mutate(prop = count / sum(count)) %>%
  filter(any(class == "white.noise" & prop >= 0.9) | (class != "white.noise")) %>%
  filter(prop == max(prop)) %>%
  ungroup() %>% 
  rename(new.class = class) %>% select(window, new.class)

> df2.sum
# A tibble: 5 x 2
  window   new.class
   <int>       <chr>
1      4 white.noise
2      5      event1
3      3      event2
4      1      event1
5      2      event1

> left_join(df2, df2.sum, by = "window")
   value       class window   new.class
1      1 white.noise      1      event1
2      1 white.noise      1      event1
3      1 white.noise      1      event1
4      2 white.noise      1      event1
5      2 white.noise      1      event1
6      1 white.noise      1      event1
7      2 white.noise      1      event1
8      1 white.noise      1      event1
9      3      event1      1      event1
10     2 white.noise      1      event1
...

答案 1 :(得分:1)

对Z.Lin的答案进行了一些改进。我认为最好先将分类逻辑包装成单独的函数。

library(dplyr)

classify_window <- function(class_vec) {
  is_white_noise <- class_vec == "white.noise"
  if (mean(is_white_noise) > 0.9) {
    return("white.noise")
  } else {
    class_no_noise <- class_vec[!is_white_noise]
    class_table <- table(class_no_noise)

    return(names(class_table)[which.max(class_table)])
  }
}

df2_summary <- df2 %>%
  group_by(window) %>%
  summarise(tag = classify_window(class))

df2_tagged <- df2 %>% left_join(y = df2_summary, by = "window")
df2_tagged