Я намагаюся подати заявку dcast
на довгій таблиці, продовження з відповіді нитки Як отримати цю структуру даних у R?
Код
dat.m <- structure(c(150L, 60L, 41L, 61L, 0L, 0L), .Dim = c(3L, 2L), .Dimnames = list(
c("ave_max", "ave", "lepo"), NULL))
library("ggplot2")
library("data.table")
dat.m <- melt(as.data.table(dat.m, keep.rownames = "Vars"), id.vars = "Vars") # https://stackoverflow.com/a/44128640/54964
dat.m
print("New step")
# http://stackoverflow.com/a/44090815/54964
minmax <- dat.m[dat.m$Vars %in% c("ave_max","lepo"), ]
absol <- dat.m[dat.m$Vars %in% c("ave"), ]
#minm <- dcast(minmax, Vars ~ variable)
minm <- dcast(minmax, Vars ~ ...)
absol <- merge(absol, minm, by = "Vars", all.x = T)
absol
#Test function
ggplot(absol, aes(x = Vars, y = value, fill = variable)) +
geom_bar(stat = "identity") +
geom_errorbar(aes(ymin = lepo, ymax = ave_max), width = .25)
Вихідні дані
dcast, melt
Vars variable value
1: ave_max V1 150
2: ave V1 60
3: lepo V1 41
4: ave_max V2 61
5: ave V2 0
6: lepo V2 0
[1] "New step"
Vars variable value V1 V2
1: ave V1 60 NA NA
2: ave V2 0 NA NA
Error in FUN(X[[i]], ...) : object "lepo" not found
Calls: <Anonymous> ... by_layer -> f -> <Anonymous> -> f -> lapply -> FUN -> FUN
Execution halted
Очікуваний результат: для проходження тестової функції ggplot
Тестування пропозиції Уве
Мета полягає в тому, щоб дістатись до цієї структури даних
dat.m <- structure(c(150L, 60L, 41L, 61L, 0L, 0L), .Dim = c(3L, 2L), .Dimnames = list(c("ave_max", "ave", "lepo"), NULL))
з цієї структури даних
dat.m <- structure(list(ave_max = c(15L, 6L), ave = c(6L, NA), lepo = c(4L, NA)), .Names = c("ave_max", "ave", "lepo"), class = "data.frame", row.names = c(NA, -2L))
Спроби
dat.m <- structure(list(ave_max = c(15L, 6L), ave = c(6L, NA), lepo = c(4L, NA)), .Names = c("ave_max", "ave", "lepo"), class = "data.frame", row.names = c(NA, -2L))
# ...
Код і вихідні дані
dat.m <- setDT(dat.m)
Неправильний результат
ave_max ave lepo 1: 15 6 4 2: 6 NA NA Classes ‘data.table’ and "data.frame": 2 obs. of 3 variables: $ ave_max: int 15 6 $ ave : int 6 NA $ lepo : int 4 NA - attr(*, ".internal.selfref")=<externalptr>
Код і вихідні дані
dat.m <- as.matrix(dcast(melt(setDT(dat.m), measure.vars = names(dat.m)), variable ~ rowid(variable))[, variable := NULL]); dimnames(dat.m) <- list(names(dat.m), NULL);
Неправильний результат
Error in `:=`(variable, NULL) : Check that is.data.table(DT) == TRUE. Otherwise, := and `:=`(...) are defined for use in j, once only and in particular ways. See help(":=").
R: 3.4.0 (бекпорти)
ОС: Debian 8.7.
Відповіді:
1 для відповіді № 1Оператор відредагував його запитання та надає дані як data.frame:
dat.df <- structure(list(ave_max = c(15L, 6L), ave = c(6L, NA), lepo = c(4L, NA)),
.Names = c("ave_max", "ave", "lepo"), class = "data.frame",
row.names = c(NA, -2L))
dat.df
# ave_max ave lepo
#1 15 6 4
#2 6 NA NA
class(dat.df)
#[1] "data.frame"
Зараз він просить перетворити цей data.frame в матрицю, подібну до тієї, яка використовується як вхідні дані в ця відповідь.
Це можна досягти, використовуючи data.table
:
library(data.table) # CRAN version 1.10.4 used
# transpose the input data frame, use rowid() to create columns,
# remove a character column to ensure matrix will be of type integer,
# finally, coerce to matrix
dat.m2 <- as.matrix(
data.table::dcast(
data.table::melt(setDT(dat.df), measure.vars = names(dat.df)),
variable ~ rowid(variable)
)[, variable := NULL]
)
# add row names, remove column names
dimnames(dat.m2) <- list(names(dat.df), NULL)
dat.m2
# [,1] [,2]
#ave_max 15 6
#ave 6 NA
#lepo 4 NA
str(dat.m2)
# int [1:3, 1:2] 15 6 4 6 NA NA
# - attr(*, "dimnames")=List of 2
# ..$ : chr [1:3] "ave_max" "ave" "lepo"
# ..$ : NULL
class(dat.m2)
#[1] "matrix"
Редагувати: Я вніс зміни до вищезазначеного коду, щоб використовувати оператор подвійної двокрапки, щоб явно вказати простір імен, з якого melt()
і dcast()
слід взяти. Зазвичай це не буде необхідним, оскільки data.table
вже завантажено. Однак OP повідомляє про проблеми, які можуть бути спричинені пакетом reshape2
завантажується після data.table
. The data.table
пакет має власні швидші реалізації reshape2::dcast()
і reshape2::melt()
. Коли обидва пакунки з якихось причин завантажені, можуть статися зіткнення імен.
1 для відповіді № 2
OP надав дані як матрицю:
dat.m <- structure(c(150L, 60L, 41L, 61L, 0L, 0L), .Dim = c(3L, 2L), .Dimnames = list(
c("ave_max", "ave", "lepo"), NULL))
# dat.m
# [,1] [,2]
#ave_max 150 61
#ave 60 0
#lepo 41 0
class(dat.m)
#[1] "matrix"
Для цього набору даних OP хоче використовувати ggplot2
створити гістограму зі стовпчиками помилок, де висота стовпчиків задається значеннями ave
а нижня і верхня межі стовпчиків помилок - lepo
і ave_max
, відповідно, у кожному стовпці.
Як ggplot2
очікує, що дані будуть подані як data.frame дані повинні бути перетворені. Для цього, data.table
використовується:
library(data.table) # CRAN version 1.10.4 used
# convert to data.table & transpose
transposed <- dcast(melt(as.data.table(dat.m, keep.rownames = "Vars"),
id.vars = "Vars"), variable ~ ...)
setnames(transposed, "variable", "Vars")
library(ggplot2)
ggplot(transposed, aes(x = Vars, y = ave, ymin = lepo, ymax = ave_max)) +
geom_col() +
geom_errorbar(width = .25)