Data.table и для циклов

#r #for-loop

#r #цикл for

Вопрос:

Я работал над проблемой с data.tables. По сути, я ищу данные.таблица для проверки set_a и проверки того, что a Average больше 80, и делаю некоторое построение матрицы. Мои критерии ищут set_a значение, и если оно больше 80, я хочу вставить только верхнее значение, как показано ниже в моем скрипте, чтобы создать строку, состоящую из set_a , set_b объединенную с буквой a, value а затем добавить другую строку с set_a , set_b объединенную с буквой b, value в основную таблицу mn. Если оно не превышает 80, чем я хочу, выберите значения 1 и 2 Average , упорядоченные по убыванию. Я смог выполнить первую часть цикла, но он не продолжается для set_a значений b и c . Вы также увидите t , где я пытался создать вторую таблицу данных для другой части цикла, но не смог получить доступ к значениям для столбцов, как обычно, в data.frames.

 Example data_set:
set_a <- c("a","a","a","a","b","b","b","b","c","c","c","c")
set_b <- c("red","red","red","red","red","red","red","red","red","red","red","red")
value <- c(42,68,90,91,22,65,89,98,78,88,91,33)
Average <- c(94,3,2,1,50,40,5,5,80,9,1,1)
a = data.frame(set_a,set_b,value,Average)
library(data.table)
a = data.table(a)
  

R-скрипт

 mn <- c() #create matrix to fill
mn0 <- c() #temp matrix
colu = unique(as.character(a$set_a))
colu2 = as.character(a$set_b)
for (i in seq_along(colu))
  {
    if (a[set_a[i] == colu[i], max(Average) > 80])#if the average is greater than 80 paste row variables in table.
  {
      mn <- (cbind(set_a[i],paste0(set_b[i],"_a"),value[i]))
      mn0 <- rbind(mn,mn0)
      mn2 <- (cbind(set_a[i],paste0(set_b[i],"_b"),value[i]))
      mn0 <- rbind(mn0,mn2)
      break
  }else

  {
    t = a[set_a == colu[i],.SD[1:2]] #create a second data table to select for
                                     #first second value  

    mn3 <- cbind(set_a[i],paste0(set_b[i],"_a"),value[i])

    mn0 <- rbind(mn0,mn3)
    mn4 <- cbind(set_a[i],paste0(set_b[i],"_b"),value[i])
    mn0 <- rbind(mn0,mn4)
  }
}

mn0
  

Мой текущий результат:

      [,1] [,2]    [,3]
[1,] "a"  "red_a" "42"
[2,] "a"  "red_b" "42"
  

Желаемый результат:

     [,1] [,2]    [,3]
[1,] "a"  "red_a" "42"
[2,] "a"  "red_b" "42"
[3,] "b"  "red_a" "22"
[4,] "b"  "red_b" "65"
[5,] "c"  "red_a" "78"
[6,] "c"  "red_b" "88"
  

Ответ №1:

У вас есть break внутри if . Это приведет к выходу вашего кода for-loop из . Также в else блоке нужно ссылаться на временную таблицу данных «t», в противном случае set_a будет ссылаться на таблицу данных «a».

Вот правильный сценарий:

 mn <- c() #create matrix to fill
mn0 <- c() #temp matrix
colu = unique(as.character(a$set_a))
colu2 = as.character(a$set_b)

for (i in seq_along(colu))
  {
    if (a[set_a == colu[i], max(Average) > 80])#if the average is greater than 80 paste row variables in table.
  {
      mn <- (cbind(set_a[i],paste0(set_b[i],"_a"),value[i]))
      mn0 <- rbind(mn,mn0)
      mn2 <- (cbind(set_a[i],paste0(set_b[i],"_b"),value[i]))
      mn0 <- rbind(mn0,mn2)
  }else

  {
    t = a[set_a == colu[i],.SD[1:2]] #create a second data table to select for
                                     #first second value  

    mn3 <- cbind(as.character(t$set_a[1]),paste0(t$set_b[1],"_a"),t$value[1])

    mn0 <- rbind(mn0,mn3)
    mn4 <- cbind(as.character(t$set_a[2]),paste0(t$set_b[2],"_b"),t$value[2])
    mn0 <- rbind(mn0,mn4)
  }
}

mn0
  

Комментарии:

1. Спасибо. Я не понимал, что вы могли бы сделать $ selection с помощью data.tables.