Как узнать, есть ли у нас два или более одинаковых минимальных значения в определенных столбцах - PullRequest
2 голосов
/ 31 мая 2019

У меня есть эта проблема, я надеялся, что кто-то может помочь.

У меня очень большой фрейм данных (около 20000000 наблюдений) в R с примерно 43 столбцами, в четырех из этих столбцов мне нужно выяснить, существует ли более одного равного минимального значения ниже 200, тогда, если у нас есть строки, где более чем один столбец имеет одно и то же значение, соответствующее этому критерию. Мне нужно пометить эту строку в TRUE (в новом столбце флага). Обратите внимание, что эти столбцы содержат значения NA, и NA s не должны использоваться (если NA присутствует в сравниваемых столбцах, возвращает NA)

цель состоит в том, чтобы найти значения в каждой строке для столбцов от a1 до a4 и определить, встречается ли минимальное значение, которое не превышает 200, в более чем одном столбце в строке

для простоты скажем, что так выглядят мои данные

head(mydata)
t1  a1  a2  a3  a4 
34  NA  NA  NA  NA
26  10  15  250 150
34  20  20  100 30 
35  5   5   10  5  
25  45  100 3   45
31 400 310 500 310 
")

цель состоит в том, чтобы найти значения в каждой строке для столбцов от a1 до a4 и выяснить, встречается ли минимальное значение, которое не превышает 200, в более чем одном столбце в строке, если оно возвращает true, если нет, false

ожидаемый результат будет выглядеть так

head(mydata)
t1  a1  a2  a3  a4  flag
34  NA  NA  NA  NA  NA
26  10  15  250 150 FALSE
34  20  20  100 30  TRUE
35  5   5   10  5   TRUE
25  45  100 3   45  FALSE
31 400 310 500 310  FALSE
")

Заранее спасибо.

Ответы [ 5 ]

3 голосов
/ 31 мая 2019

Вот базовый способ R сделать это

#Get the column indices where a1, a2, a3 and a4 are there
inds <- match(paste0("a", 1:4), names(df))

#Get row-wise minimum
min_val <- do.call(pmin, df[inds])

#Check if there are more than one occurrence of minimum value 
# and if minimum value is less than 200.
df$flag <- rowSums(df[inds] == min_val) > 1 & min_val < 200

df
#  t1  a1  a2  a3  a4  flag
#1 34  NA  NA  NA  NA    NA
#2 26  10  15 250 150 FALSE
#3 34  20  20 100  30  TRUE
#4 35   5   5  10   5  TRUE
#5 25  45 100   3  45 FALSE
#6 31 400 310 500 310 FALSE
2 голосов
/ 31 мая 2019

Вам это помогает?:

mydata$flag=apply(mydata,1,function(x){  # iterate through rows
    x=na.omit(x);        # omit NAs in a row (optional)
    tab=table(x[x<200]); # count numbers of all row values below 200
    if(any(tab>1)){      # check if any values are not unique
          return(TRUE)
          }else{
          return(FALSE)
         }})

Вы можете включить или пропустить NA значения или нет.

0 голосов
/ 31 мая 2019

Если у вас большой набор данных, следующее может быть быстрым.Используется пакет matrixStats, функция rowMins.См. этот ответ .

icol <- grepl("^a", names(mydata))
min_row <- matrixStats::rowMins(as.matrix(mydata[icol]))

mydata$flag <- rowSums(mydata[icol] == min_row) > 1 & min_row < 200
0 голосов
/ 31 мая 2019

Одна возможность с участием dplyr и purrr:

df %>%
 mutate(flag = exec(pmin, !!!.[-1]),
        flag = rowSums(.[-1] == flag) > 1 & flag < 200)

  t1  a1  a2  a3  a4  flag
1 34  NA  NA  NA  NA    NA
2 26  10  15 250 150 FALSE
3 34  20  20 100  30  TRUE
4 35   5   5  10   5  TRUE
5 25  45 100   3  45 FALSE
6 31 400 310 500 310 FALSE

Здесь он проверяет, является ли появление строчного минимума больше 1 и меньше ли строчный минимум 200.

0 голосов
/ 31 мая 2019

Вот решение purrr. Я создаю фрейм данных.

# Define data frame
df <- read.table(text = " t1  a1  a2  a3  a4 
                  34  NA  NA  NA  NA
                  26  10  15  250 150
                  34  20  20  100 30 
                  35  5   5   10  5  
                  25  45  100 3   45
                  31 400 310 500 310 ", header = TRUE)

Далее я загружаю библиотеку.

# Load library
library(purrr)

Затем я создаю флаг, проходящий через каждую строку, используя pmap_lgl, который возвращает логическое значение. Эта строка проверяет, существует ли более одного минимального значения и , что минимальное значение меньше 200. Первый столбец в расчетах не указывается. Если в каждой строке есть значения NA, будет создан NA.

# Create flag
df$flag <- pmap_lgl(df, function(...)(sum(c(...)[-1] == min(c(...)[-1])) > 1) & min(c(...)[-1]) < 200)

Это дает следующее:

# Examine result
df
#>   t1  a1  a2  a3  a4  flag
#> 1 34  NA  NA  NA  NA    NA
#> 2 26  10  15 250 150 FALSE
#> 3 34  20  20 100  30  TRUE
#> 4 35   5   5  10   5  TRUE
#> 5 25  45 100   3  45 FALSE
#> 6 31 400 310 500 310 FALSE

Создано в 2019-05-31 пакетом представ. (v0.3.0)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...