1

given the following data:

location = c("A", "A", "A", "B", "B")
day = c("Mon","Mon","Mon","Tue", "Tue")
type = c("road", "scan", "fly", "road", "fly")

dat <- data.frame(location,day, type) 


location day    type
   A       Mon  road
   A       Mon  scan
   A       Mon  fly
   B       Tue  road
   B       Tue  fly

I need a way to wrangle this so that it looks like this

location day road scan fly
     A    Mon   1   1   1
     B    Tue   1   0   1

maybe with spread?

user1658170
  • 814
  • 2
  • 14
  • 24
  • 2
    Use `reshape2::dcast(dat, location + day ~ type, fun = length)` – markus Jan 04 '19 at 20:39
  • Related [How to reshape data from long to wide format?](https://stackoverflow.com/questions/5890584/how-to-reshape-data-from-long-to-wide-format) – markus Jan 04 '19 at 20:41
  • If you're dealing with large data, I recommend using data.table, it will provide significant speed improvements. – Khaynes Jan 04 '19 at 20:57
  • alternative: `dat %>% mutate(n = 1) %>% tidyr::spread(type,n, fill = 0)` – Mankind_008 Jan 04 '19 at 20:58
  • https://cran.r-project.org/web/packages/data.table/vignettes/datatable-reshape.html is a really useful read as well – Khaynes Jan 04 '19 at 20:58

1 Answers1

2

We can use tiudyverse. Get the frequency grouped by 'location', 'day', 'type' with count and spread to 'wide' format

library(tidyverse)
dat %>% 
  count(location, day, type) %>% 
  spread(type, n, fill = 0)
# A tibble: 2 x 5
#  location day     fly  road  scan
#  <fct>    <fct> <dbl> <dbl> <dbl>
#1 A        Mon       1     1     1
#2 B        Tue       1     1     0

A base R option with aggregate and reshape

reshape(aggregate(val ~ ., transform(dat, val = 1), length), 
    idvar = c('location', 'day'), direction = 'wide', timevar = 'type')
akrun
  • 874,273
  • 37
  • 540
  • 662