Последовательное переименование повторяющегося значения в символьной переменной перед преобразованием его в dcast - PullRequest
0 голосов
/ 01 апреля 2019

Я собираю информацию об автомобилях с веб-сайта и получаю не постоянные и не очень чистые данные.Я пытаюсь очистить и упорядочить эти данные во фрейм данных.

Например:

dd <- data.frame(measure = c("wheel", "wheel", "length", "width", "wheel", "width"), value = 1:6, model = "a", stringsAsFactors = F)
dd
  measure value model
1   wheel     1     a
2   wheel     2     a
3  length     3     a
4   width     4     a
5   wheel     5     a
6   width     6     a

В этом примере у меня есть 3 значения wheel и 2 значения width.В моих реальных данных, это не всегда одно и то же, что повторяется, оно может иметь или не иметь повторение, и это может повторяться более одного раза.

Мне нужно изменить форму этой таблицы, чтобы иметь одну строку на model, однако я не хочу агрегировать value, которые имеют общий measure.Точно, я хотел бы, чтобы таблица стала:

  model length wheel wheel1 wheel2 width width1
1     a      3     1      2      5     4      6

Это было получено с помощью dcast на вручную измененных данных:

library(reshape2)    
res <- data.frame(measure = c("wheel", "wheel1", "length", "width", "wheel2", "width1"), value = 1:6, model = "a", stringsAsFactors = F)
dcast(res, model ~ measure)

Мне нужен любой способ изменить dcastпоэтому он не агрегирует measure и не автоматически изменяет dd, поэтому он становится res.

Я пробовал что-то уродливое и не совсем то, что мне было нужно:

dd[duplicated(dd$measure), "measure"] <- paste0(dd[duplicated(dd$measure), "measure"] , 1:3)
dd
  measure value model
1   wheel     1     a
2  wheel1     2     a
3  length     3     a
4   width     4     a
5  wheel2     5     a
6  width3     6     a

Этот код не работает, потому что width получает индекс 3, а не 2.Кроме того, это не подстраивается под другую таблицу, например:

dd2 <- data.frame(measure = c("wheel", "wheel", "length", "width", "wheel"), value = 1:5, model = "a", stringsAsFactors = F)
dd2[duplicated(dd2$measure), "measure"] <- paste0(dd2[duplicated(dd2$measure), "measure"] , 1:3)
Error in `[<-.data.frame`(`*tmp*`, duplicated(dd2$measure), "measure",  : 
  replacement has 3 rows, data has 2

В любом случае, как я могу динамически изменить переменную measure, чтобы все слова были уникальными?

Ответы [ 4 ]

1 голос
/ 01 апреля 2019

make.unique делает именно это:

dd$measure <- make.unique(dd$measure,sep = "")  
dd            
#    measure value model
# 1   wheel     1     a
# 2  wheel1     2     a
# 3  length     3     a
# 4   width     4     a
# 5  wheel2     5     a
# 6  width1     6     a
1 голос
/ 01 апреля 2019

Другая tidyverse возможность может быть:

dd %>%
 arrange(model, measure) %>%
 group_by(model, measure) %>%
 mutate(var = paste(measure, seq_along(measure), sep = "_")) %>%
 ungroup() %>%
 select(-measure) %>%
 spread(var, value)

  model length_1 wheel_1 wheel_2 wheel_3 width_1 width_2
  <chr>    <int>   <int>   <int>   <int>   <int>   <int>
1 a            3       1       2       5       4       6
1 голос
/ 01 апреля 2019

Можете ли вы использовать dplyr::mutate, как показано ниже:

dd <- dd %>%
  group_by(model, measure) %>%
  mutate(measure2 = paste0(measure, ifelse(row_number() > 1, row_number() - 1, ""))) %>%
  ungroup() %>%
  mutate(measure = measure2) %>%
  select(measure, model, value)
dd
# A tibble: 6 x 3
  measure model value
  <chr>   <chr> <int>
1 wheel   a         1
2 wheel1  a         2
3 length  a         3
4 width   a         4
5 wheel2  a         5
6 width1  a         6
0 голосов
/ 01 апреля 2019

Вы также можете изменить нумерацию значений на sapply

sapply(unique(dd$measure), function(x) {
  z <- dd$measure[dd$measure %in% x]
  if (length(z) > 1)
  dd$measure[dd$measure %in% x] <<- paste0(z, ".", seq(length(z)))
})

и используйте reshape после.

reshape(dd, direction="wide", timevar="measure", idvar="model")
#   model value.wheel.1 value.wheel.2 value.length value.width.1 value.wheel.3 value.width.2
# 1     a             1             2            3             4             5             6

Данные

dd <- structure(list(measure = c("wheel", "wheel", "length", "width", "wheel", "width"), 
                     value = 1:6, model = c("a", "a", "a", "a", "a", "a")), 
                class = "data.frame", row.names = c(NA, -6L))
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...