简体   繁体   English

同一组中正负匹配-R

[英]Matching of positive to negative numbers in the same group - R

I would like to do the following thing: 我想做以下事情:

id calendar_week value
1    1              10
2    2              2
3    2             -2
4    2              3
5    3              10 
6    3             -10

The output which I want is the list of id (or the rows) which have a positiv to negative match for a given calendar_week -> which means I want for example the id 2 and 3 because there is a match of -2 to 2 in Calendar week 2. I don't want id 4 because there is no -3 value in calendar week 2 and so on. 我想要的输出是ID(或行)的列表,这些列表对给定的calendar_week具有负匹配的正数->这意味着我想要例如ID 2和3,因为在其中-2到2匹配日历第2周。我不需要id 4,因为在日历第2周中没有-3值,依此类推。

output: 输出:

id calendar_week value 
2    2              2
3    2             -2
5    3              10 
6    3             -10

Could also do: 也可以做:

library(dplyr)

df %>%
  group_by(calendar_week, ab = abs(value)) %>%
  filter(n() > 1) %>% ungroup() %>%
  select(-ab)

Output: 输出:

# A tibble: 4 x 3
     id calendar_week value
  <int>         <int> <int>
1     2             2     2
2     3             2    -2
3     5             3    10
4     6             3   -10

Given your additional clarifications, you could do: 考虑到您的其他说明,您可以执行以下操作:

df %>%
  group_by(calendar_week, value) %>%
  mutate(idx = row_number()) %>%
  group_by(calendar_week, idx, ab = abs(value)) %>%
  filter(n() > 1) %>% ungroup() %>%
  select(-idx, -ab)

On a modified data frame: 在修改的数据框上:

  id calendar_week value
1  1             1    10
2  2             2     2
3  3             2    -2
4  3             2     2
5  4             2     3
6  5             3    10
7  6             3   -10
8  7             4    10
9  8             4    10

This gives: 这给出:

# A tibble: 4 x 3
     id calendar_week value
  <int>         <int> <int>
1     2             2     2
2     3             2    -2
3     5             3    10
4     6             3   -10

Using tidyverse : 使用tidyverse

library(tidyverse)

df %>%
  group_by(calendar_week) %>%
  nest() %>%
  mutate(values = map_chr(data, ~ str_c(.x$value, collapse = ', '))) %>%
  unnest() %>%
  filter(str_detect(values, as.character(-value))) %>%
  select(-values)

Output : 输出:

calendar_week    id value
          <dbl> <int> <dbl>
1             2     2     2
2             2     3    -2
3             3     5    10
4             3     6   -10

If as stated in the comments only a single match is required you could try: 如果如评论中所述,仅需进行一次匹配,则可以尝试:

library(dplyr)

df %>%
  group_by(calendar_week, nvalue = abs(value)) %>% 
  filter(!duplicated(value)) %>%
  filter(sum(value) == 0) %>% 
  ungroup() %>%
  select(-nvalue)

     id calendar_week value
  <int>         <int> <int>
1     2             2     2
2     3             2    -2
3     5             3   -10
4     6             3    10

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM