Измените длинную структурированную таблицу данных в широкую структуру, используя функции data.table?
> library(data.table)
> A <- data.table(x = c(1,1,2,2), y = c(1,2,1,2), v = c(0.1,0.2,0.3,0.4))
> A
x y v
1: 1 1 0.1
2: 1 2 0.2
3: 2 1 0.3
4: 2 2 0.4
> B <- dcast(A, x~y)
Using v as value column: use value.var to override.
> B
x 1 2
1 1 0.1 0.2
2 2 0.3 0.4
По-видимому, я могу изменить таблицу данных с длинного на широкий, используя f.x. dcast пакета reshape2. Но data.table поставляется вместе с перегруженным оператором-скотчем, предлагающим такие параметры, как "by" и "group", которые заставляют меня задаться вопросом, можно ли достичь этого с помощью этого (для конкретных функций данных)?
Только один случайный пример из руководства:
DT[,lapply(.SD,sum),by=x]
Это выглядит потрясающе - но я пока не совсем понимаю его использование.
Я не нашел пути и примера для этого, так что, возможно, это просто невозможно, возможно, это даже не должно быть - так что определенная "нет, не возможна, потому что..." тогда, конечно, действительный ответ.
Ответы
Ответ 1
Я возьму пример с неравными группами, чтобы было проще проиллюстрировать общий случай:
A <- data.table(x=c(1,1,1,2,2), y=c(1,2,3,1,2), v=(1:5)/5)
> A
x y v
1: 1 1 0.2
2: 1 2 0.4
3: 1 3 0.6
4: 2 1 0.8
5: 2 2 1.0
Первый шаг - получить количество элементов/записей для каждой группы "x" одинаково. Здесь для x = 1 существует 3 значения y, но только 2 при x = 2. Итак, сначала мы должны исправить это с помощью NA для x = 2, y = 3.
setkey(A, x, y)
A[CJ(unique(x), unique(y))]
Теперь, чтобы получить его в широком формате, мы должны группировать "x" и использовать as.list
на v
следующим образом:
out <- A[CJ(unique(x), unique(y))][, as.list(v), by=x]
x V1 V2 V3
1: 1 0.2 0.4 0.6
2: 2 0.8 1.0 NA
Теперь вы можете установить имена перестроенных столбцов, используя ссылку с setnames
следующим образом:
setnames(out, c("x", as.character(unique(A$y)))
x 1 2 3
1: 1 0.2 0.4 0.6
2: 2 0.8 1.0 NA
Ответ 2
Используйте dcast()
(теперь по умолчанию метод data.table
, начиная с версии 1.9.5, более ранние версии используют dcast.data.table
), как в
> dcast(A,x~y)
Using 'v' as value column. Use 'value.var' to override
x 1 2 3
1: 1 0.2 0.4 0.6
2: 2 0.8 1.0 NA
Это быстро и устраняет необходимость setnames()
.
Также особенно полезно, когда y
в приведенном выше примере является фактор-переменной с уровнями символов - например, "Низкий", "Средний", "Высокий" - потому что CJ()
может не возвращать широкие данные с переменными в том порядке, в котором ожидаются setnames()
, и вы можете плохо потерять свои данные.
Ответ 3
(с кредитами Аруну)
A[, setattr(as.list(v), 'names', y), by=x]