根据条件提取值

问题描述 投票:0回答:2

我有以下示例数据集,其中包含两个变量(Ip 和 Ge),它们可以包含一个、两个(或多个)值,并用“;”分隔。 Ip 中的每个值都按照其顺序与 Ge 的值相关联(例如:第 3 行:Abri 与 Ibr 相关联,Echo 与 Tyh 相关联)

Data_test= data.frame(Ip=c("Abri", "Abri", "Abri;Echo", "Echo", "Abri;Abri", "Echo;Abri", "Abri", "Abri;Abri;Echo", "Abri;Abri"), 
           Ge=c("Aju", "Jlt", "Ibr;Tyh", "Rtj", "Ekm;Bty", "Itz;Orv", "Adr", "Dhu;Vfr;Lnh", "Tde;Ijp"), 
           Ca=c(2,13,4,2, 4, 6, 13, 13, 4), Mp=c(5,5,4,3,10,1,17, 15, 2))

Data_test

              Ip          Ge Ca Mp
1           Abri         Aju  2  5
2           Abri         Jlt 13  5
3      Abri;Echo     Ibr;Tyh  4  4
4           Echo         Rtj  2  3
5      Abri;Abri     Ekm;Bty  4 10
6      Echo;Abri     Itz;Orv  6  1
7           Abri         Adr 13 17
8 Abri;Abri;Echo Dhu;Vfr;Lnh 13 15
9      Abri;Abri     Tde;Ijp  4  2


我想在另一个变量中提取 Ge 中的值,具体取决于 Ip、Ca 和 Mp 中的值,遵循以下规则:

-> (1) 提取与 Echo 相关的所有值
-> (2) 提取与 Abri 和(Ca>9 和/或 Mp>8)相关的所有值

输出将是

> Output_test
              Ip          Ge Ca Mp     Outpout
1           Abri         Aju  2  5        <NA>
2           Abri         Jlt 13  5         Jlt
3      Abri;Echo     Ibr;Tyh  4  4         Tyh
4           Echo         Rtj  2  3         Rtj
5      Abri;Abri     Ekm;Bty  4 10     Ekm;Bty
6      Echo;Abri     Itz;Orv  6  1         Itz
7           Abri         Adr 13 17         Adr
8 Abri;Abri;Echo Dhu;Vfr;Lnh 13 15 Dhu;Vfr;Lnh
9      Abri;Abri     Tde;Ijp  4  2        <NA>

我尝试使用 mutate 和 ifelse 来做到这一点,但我不知道如何处理 Ip 和 Ge 包含多个值的情况。任何帮助将不胜感激

library(tidyverse)

Data_test %>% 
  mutate(Output=ifelse(Ip=="Echo", Ge, 
                       ifelse(Ip=="Abri" & (Ca>9 | Mp>8), Ge, 
                       ifelse( , , ))))
r extract
2个回答
0
投票

我们可以将

Ip
Ge
列拆分为在
";"
上拆分的单独行。我认为如果我们有整齐格式的数据,处理会更容易。我们还创建了一个
row
列,用于在拆分之前跟踪原始行号。

使用

case_when
应用条件并将每个
row
的所有值集中在一列中。

library(dplyr)
library(tidyr)

Data_test %>%
  mutate(row = row_number()) %>%
  separate_longer_delim(c(Ip, Ge), ";") %>%
  mutate(Output = case_when(
    Ip == "Echo" ~ Ge, 
    Ip == "Abri" & (Ca > 9 | Mp >8) ~ Ge, 
    .default = NA_character_
  )) %>%
  summarise(across(c(Ip, Ge, Output), ~paste0(na.omit(.), collapse = ";")), 
            across(c(Ca, Mp), first),
            Output = na_if(Output, ""),
            .by = "row") %>%
  select(-row) %>%
  relocate(Output, .after = last_col())

#.             Ip          Ge Ca Mp      Output
#1           Abri         Aju  2  5        <NA>
#2           Abri         Jlt 13  5         Jlt
#3      Abri;Echo     Ibr;Tyh  4  4         Tyh
#4           Echo         Rtj  2  3         Rtj
#5      Abri;Abri     Ekm;Bty  4 10     Ekm;Bty
#6      Echo;Abri     Itz;Orv  6  1         Itz
#7           Abri         Adr 13 17         Adr
#8 Abri;Abri;Echo Dhu;Vfr;Lnh 13 15 Dhu;Vfr;Lnh
#9      Abri;Abri     Tde;Ijp  4  2        <NA>

0
投票

使用

pmap()

Data_test |> 
 mutate(i = str_split(Ip, ";"),
        g = str_split(Ge, ";"),
        Output = pmap_chr(list(i, g, Ca, Mp), \(i, g, a, m) paste0(c(g[i == "Echo"], g[i == "Abri" & (a > 9 | m > 8)]), collapse = ";")) %>% {if_else(. == "", NA_character_, .)}) |>
 select(-i, -g)
© www.soinside.com 2019 - 2024. All rights reserved.