Эмуляция reshape2 :: melt с pivot_longer для матриц - PullRequest
2 голосов
/ 28 февраля 2020

Я просто попытался использовать pivot_longer на 2D-матрице, чтобы получить «аккуратные» данные для ggplot. До сих пор это было довольно просто с reshape2::melt

library(tidyverse)
library(reshape2)

x <- c(1, 2, 3, 4)
y <- c(1, 2, 3)

Data      <- matrix(round(rnorm(12, 10, 4)), nrow = 4, ncol = 3)
melt_data <- reshape2::melt(Data)

ggplot2::ggplot(meltvec, ggplot2::aes(x = Var1, y = Var2, fill = value)) +
   geom_tile()

Однако pivot_longer нужен тиббл или data.frame. Итак, я придумал следующую функцию:

matrix_longer <- function(.data){
  stopifnot(is.matrix(.data),
            !is.data.frame(.data))

  .data <- as.data.frame(.data)
  names(.data) <- 1:ncol(.data)

  .data$Var1 =1:nrow(.data)

   pivot_longer(.data,cols = as.character( 1:(ncol(.data)-1)), names_to = "Var2", values_to = "value") %>% 
     arrange(Var2) %>% 
     mutate(Var2=as.numeric(Var2))
 }

И он выдает тот же результат

own_data <- matrix_longer(Data)

ggplot2::ggplot(own_data, ggplot2::aes(x = Var1, y = Var2, fill = value)) +
   geom_tile()

all(own_data==melt_data)

Вопрос: есть ли лучшее решение? Должен ли я / я просто придерживаться reshape2::melt? Это плохая идея использовать .data?

1 Ответ

3 голосов
/ 28 февраля 2020

Чтобы получить трехколонный массив данных индексов строк и столбцов и значений из матрицы, вы можете просто использовать as.data.frame.table():

set.seed(9)
Data <- matrix(round(rnorm(12, 10, 4)), nrow = 4, ncol = 3)

as.data.frame.table(Data, responseName = "value")

   Var1 Var2 value
1     A    A    10
2     B    A     9
3     C    A    17
4     D    A     7
5     A    B    10
6     B    B     0
7     C    B    14
8     D    B     7
9     A    C    17
10    B    C    11
11    C    C     9
12    D    C    14

Если вы хотите, чтобы индексы были целыми числами, а не alphanumeri c значения (факторы по умолчанию) вы можете сделать:

library(dplyr)

as.data.frame.table(Data, responseName = "value") %>%
  mutate_if(is.factor, as.integer)

   Var1 Var2 value
1     1    1    10
2     2    1     9
3     3    1    17
4     4    1     7
5     1    2    10
6     2    2     0
7     3    2    14
8     4    2     7
9     1    3    17
10    2    3    11
11    3    3     9
12    4    3    14
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...