【问题标题】:Remove rows with the same values by consecutive wave in R通过R中的连续波删除具有相同值的行
【发布时间】:2020-08-31 17:54:54
【问题描述】:

我有一个按波显示友谊关系的面板数据框。我想删除连续波中出现的友谊关系,只保留不连续的友谊关系。

我所说的非连续友谊关系是指如果 A 在时间 1 和时间 3 提名 B 作为他们的朋友,但不是时间 2。

HAVE 数据示例:

id   friend   wave
1    4        1
1    5        1
1    2        2
1    5        3
1    2        3
2    1        1
2    4        1
2    1        2
2    1        3
4    3        1
4    5        2
4    3        3
5    1        1 
5    3        2
5    4        2
5    2        3
6    5        1
6    5        2
6    5        4

想要数据:

 id   friend   wave
 1    5        1
 1    5        3
 4    3        1
 4    3        3
 6    5        2
 6    5        4

【问题讨论】:

  • 啊-你是对的,修好了。谢谢!
  • 您的定义不清楚。如果你有数据集df <- tibble(id = c(6,6,6), friend = c(5,5,5), wave = c(1,2,4)) - 你想保留第二行吗?它与其前身是连续的,但与其后继者不连续。
  • @DavidT 在该示例的情况下,我想保留第 2 行和第 4 行,因为 id =6 和friend = 5 没有出现在 wave = 3 中。
  • 好吧,这些数据将被@RonakShaw 的df %>% group_by(id, friend) %>% filter(n() > 1 && all(diff(wave) != 1)) 排除在外。我认为您正在尝试选择idfriend 相同的记录对,并且wave 之间存在间隙,即使这两条记录都是连续的其他记录。但是看看你的示例代码,我不确定。
  • 好的,所以我在下面发布了一个替代解决方案。

标签: r dplyr time-series data-manipulation


【解决方案1】:

正如我在 cmets 中所说,我们正在选择 id, friend 相同的记录对,并且波浪之间存在间隙,即使这两条记录与其他记录是连续的。在您的数据中添加几条记录:

df <- read_table("id   friend   wave
1    4        1
1    5        1
1    2        2
1    5        3
1    2        3
2    1        1
2    4        1
2    1        2
2    1        3
4    3        1
4    5        2
4    3        3
5    1        1 
5    3        2
5    4        2
5    2        3
6    5        1
6    5        2
6    5        4") %>% 
  as_tibble() 

添加 leadlag 列。

interm <- df %>% 
  group_by(id, friend) %>% 
    # wave has to be in ascending order for the 'lead' and 'lag
  arrange(id, friend, wave) %>% 
  mutate(next_wave = lead(wave, default = NA),
         prev_wave = lag(wave, default = NA),
           # Keep any that have a wave-difference > 1, ahead or behind.
           # This is the tricky part.
         keep = (next_wave - wave > 1) | 
           (wave - prev_wave > 1))

到目前为止我们有什么?

R > interm
# A tibble: 19 x 6
# Groups:   id, friend [12]
      id friend  wave next_wave prev_wave keep 
   <dbl>  <dbl> <dbl>     <dbl>     <dbl> <lgl>
 1     1      4     1        NA        NA NA   
 2     1      5     1         3        NA TRUE 
 3     2      1     1         2        NA NA   
 4     2      4     1        NA        NA NA   
 5     4      3     1         3        NA TRUE 
 6     5      1     1        NA        NA NA   
 7     6      5     1         2        NA NA   
 8     1      2     2         3        NA NA   
 9     2      1     2         3         1 FALSE
10     4      5     2        NA        NA NA   
11     5      3     2        NA        NA NA   
12     5      4     2        NA        NA NA   
13     6      5     2         4         1 TRUE 
14     1      5     3        NA         1 TRUE 
15     1      2     3        NA         2 NA   
16     2      1     3        NA         2 NA   
17     4      3     3        NA         1 TRUE 
18     5      2     3        NA        NA NA   
19     6      5     4        NA         2 TRUE 

看起来正确,即使有点马虎。让我们清理一下。

answer <- interm %>% 
  filter(keep) %>% 
  select(- next_wave, - prev_wave) %>%
  ungroup()

answer
# A tibble: 6 x 4
     id friend  wave keep 
  <dbl>  <dbl> <dbl> <lgl>
1     1      5     1 TRUE 
2     1      5     3 TRUE 
3     4      3     1 TRUE 
4     4      3     3 TRUE 
5     6      5     2 TRUE 
6     6      5     4 TRUE 

【讨论】:

    【解决方案2】:

    对于每个idfriend,我们可以选择具有多于1 行的组,并且所有wave 值之间的差异不为1。

    这可以使用dplyr来完成

    library(dplyr)
    df %>% group_by(id, friend) %>% filter(n() > 1 && all(diff(wave) != 1))
    
    #     id friend  wave
    #  <int>  <int> <int>
    #1     1      5     1
    #2     1      5     3
    #3     4      3     1
    #4     4      3     3
    

    基础R:

    subset(df, as.logical(ave(wave, id, friend, FUN = function(x)
                          length(x) > 1 && all(diff(x) != 1))))
    

    data.table

    library(data.table)
    setDT(df)[, .SD[.N > 1 && all(diff(wave) != 1)], .(id, friend)]
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2021-09-12
      • 2020-01-08
      • 1970-01-01
      • 2014-04-21
      • 1970-01-01
      • 1970-01-01
      • 2017-09-20
      • 1970-01-01
      相关资源
      最近更新 更多