Tdebeus
Tdebeus

Reputation: 1599

Unnest function only keeps first value in list

I'm trying to do a seemingly simple task of unlisting a single column. I searched stackoverflow and it seems that I should use the tidyr::unnest() function. Only when I apply this function it only keeps the first valu of the vectored list in a single cell of the dataframe.

A sample of my data:

library(tidyr)

df <- structure(list(properties.referentie = c("SDE1786673", "SDE1625351", 
"SDE1636716"), geometry.coordinates = list(c(4.75813599901064, 
52.272456042152), c(6.00720800022323, 51.9725940422743), c(4.51752499877652, 
52.1393440422071))), .Names = c("properties.referentie", "geometry.coordinates"
), row.names = c(NA, -3L), class = c("tbl_df", "tbl", "data.frame"
))

My code with the incomplete output:

unnest(df, geometry.coordinates)

# A tibble: 6 x 2
  properties.referentie geometry.coordinates
  <chr>                                <dbl>
1 SDE1786673                            4.76
2 SDE1786673                           52.3 
3 SDE1625351                            6.01
4 SDE1625351                           52.0 
5 SDE1636716                            4.52
6 SDE1636716                           52.1

I actually want to create two columns out of the geometry.coordinates column.

The first row and second column contains the following value: c(4.75813599901064, 52.272456042152) so I want one column with 4.75813599901064 and another column with the other value in that vector 52.272456042152. It's lat and lon data.

Upvotes: 1

Views: 1131

Answers (3)

akrun
akrun

Reputation: 887981

After unnesting, we can spread to 'wide' format

library(tidyverse)
df %>% 
  unnest(geometry.coordinates) %>% 
  group_by(properties.referentie) %>% 
  mutate(rn = paste0("geometry.coordinates", row_number())) %>% 
  spread(rn, geometry.coordinates)
# A tibble: 3 x 3
# Groups: properties.referentie [3]
#    properties.referentie geometry.coordinates1 geometry.coordinates2    
#     <chr>                                 <dbl>                 <dbl>
# 1 SDE1625351                             6.01                  52.0
# 2 SDE1636716                             4.52                  52.1
# 3 SDE1786673                             4.76                  52.3

Or this can be done before the unnest by converting it to a list

df %>% 
    mutate(geometry.coordinates = map(geometry.coordinates,
                        ~as.list(.) %>% 
                           set_names(paste0("geometry.coordinates", seq_along(.x))) %>% 
                           as_tibble))  %>% 
    unnest
# A tibble: 3 x 3
#   properties.referentie geometry.coordinates1 geometry.coordinates2    
#    <chr>                                 <dbl>                 <dbl>    
# 1 SDE1786673                             4.76                  52.3
# 2 SDE1625351                             6.01                  52.0
# 3 SDE1636716                             4.52                  52.1

NOTE: Both the solutions work for any length within each list elements

Upvotes: 1

Birger
Birger

Reputation: 1141

Another solution from tidyverse:

df %>% 
  unnest() %>% 
  group_by(properties.referentie) %>% 
  summarise(lat = first(geometry.coordinates), lon = last(geometry.coordinates))

# A tibble: 3 x 3
  properties.referentie   lat   lon
  <chr>                 <dbl> <dbl>
1 SDE1625351             6.01  52.0
2 SDE1636716             4.52  52.1
3 SDE1786673             4.76  52.3

Upvotes: 3

BENY
BENY

Reputation: 323396

IIUC, you can using sapply with unlist to create the columns from list type column.

cbind(df$properties.referentie,data.frame(t(sapply(df$geometry.coordinates,unlist))))
  df$properties.referentie       X1       X2
1               SDE1786673 4.758136 52.27246
2               SDE1625351 6.007208 51.97259
3               SDE1636716 4.517525 52.13934

Upvotes: 0

Related Questions