Вложенный список подмножеств - PullRequest
0 голосов
/ 05 февраля 2019

У меня есть вложенный список, и я хочу выполнить фильтрацию по нескольким условиям.Я знаю, что подобные вопросы задавались, но по какой-то причине подходы, которые там есть, не будут работать в моем списке, ..

myList <- list(list(list(FileName = list("05_C13_1.mzML"), Molecule = "Adenine", 
            Adduct = list("2M+H"), cons.Area = list(42158.2196614537))), 
            list(list(FileName = list("05_C13_2.mzML"), Molecule = "Phenylalanine", 
            Adduct = list("2M+H"), cons.Area = list(36879.9850931971))), 
            list(list(FileName = list("10_C13_2.mzML", "10_C13_2.mzML"), 
            Molecule = "Adenine", Adduct = list("M+K", "M+K"), cons.Area = list(
            512368.044002373, 60847.2653549584))))

Я попробовал эту функцию:

get_sublist <- function(lst, group_name) {
                lst[lapply(lst, function(x) x[[1]][[1]]) == group_name]
}

Это работает очень хорошо в следующем списке, но по причинам, которые я не понимаю, не по моему (также, если я заменю x[[1]][[1]] на x[[1]]), ..

ThisListWorks <- list(list(list(group = "a", def = "control")), list(list(group = "b", 
        def = "disease1")))

Желаемый вывод для моего примеранапример:

SubList1 <- get_sublist(myList, "Adenine")

SubList1
list(list(list(FileName = list("05_C13_1.mzML"), Molecule = "Adenine", 
    Adduct = list("2M+H"), cons.Area = list(42158.2196614537))), 
    list(list(FileName = list("10_C13_2.mzML", "10_C13_2.mzML"), 
    Molecule = "Adenine", Adduct = list("M+K", "M+K"), cons.Area = list(
    512368.044002373, 60847.2653549584))))

или:

SubList2 <- get_sublist(myList, "10_C13_2.mzML")

SubList2
list(list(list(FileName = list("10_C13_2.mzML", "10_C13_2.mzML"), 
    Molecule = "Adenine", Adduct = list("M+K", "M+K"), cons.Area = list(
    512368.044002373, 60847.2653549584))))

1 Ответ

0 голосов
/ 05 февраля 2019

Я думаю, что используемый вами индекс (x[[1]][[1]]) неверен.Он будет искать Adenine в записи FileName.

Вы можете изменить функцию на более надежную:

get_sublist <- function(lst, var, group_name) {
  lst[lapply(lst, function(x) x[[1]][[var]]) == group_name]
}

Тогда:

xx <- get_sublist(myList, var = "Molecule", group_name = "Adenine")
dput(xx)
list(list(list(FileName = list("05_C13_1.mzML"), Molecule = "Adenine", 
    Adduct = list("2M+H"), cons.Area = list(42158.2196614537))), 
    list(list(FileName = list("10_C13_2.mzML", "10_C13_2.mzML"), 
        Molecule = "Adenine", Adduct = list("M+K", "M+K"), cons.Area = list(
            512368.044002373, 60847.2653549584))))

Это будет работать всякий раз, когда уровень var не является list.Для вашего второго примера у вас есть дополнительный уровень, и тогда вышеуказанный подход не будет работать.

Я думаю, что ваш первый уровень бесполезен в этой проблеме, поэтому я отбросил его и создал рекурсивную функцию для обработки любого количества уровней:

get_sublist <- function(lst, var, group_name) {

  if(!(var %in% names(lst))){
    pos <- sapply(X = lst, FUN = get_sublist, var = var, group_name = group_name)
  } else{
    if(is.list(lst[[var]])){
      values <- unlist(lst[[var]])
    } else{
      values <- lst[[var]]
    }

    if(group_name %in% values){
      return(TRUE)
    } else{
      return(FALSE)
    }
  } 

  lst[pos]
}

Затем:

xx <- get_sublist(unlist(myList, recursive = F), var = "Molecule", group_name = "Adenine")
dput(xx)
list(list(FileName = list("05_C13_1.mzML"), Molecule = "Adenine", 
    Adduct = list("2M+H"), cons.Area = list(42158.2196614537)), 
    list(FileName = list("10_C13_2.mzML", "10_C13_2.mzML"), Molecule = "Adenine", 
        Adduct = list("M+K", "M+K"), cons.Area = list(512368.044002373, 
            60847.2653549584)))

и,

yy <- get_sublist(unlist(myList, recursive = F), var = "FileName", group_name = "10_C13_2.mzML")
dput(yy)
list(list(FileName = list("10_C13_2.mzML", "10_C13_2.mzML"), 
    Molecule = "Adenine", Adduct = list("M+K", "M+K"), cons.Area = list(
        512368.044002373, 60847.2653549584)))
...