在不知道密钥的情况下从R dataframe中提取嵌套的JSON

时间:2017-10-10 20:53:01

标签: json r dplyr purrr

我正在尝试从TSV列中提取JSON。难点在于JSON是浅层嵌套的,并且键值可能不会出现在每一行中。

我有一个很小的例子来说明我的观点。

  df <- tibble(index = c(1, 2),
   data = c('{"json_char":"alpha", "json_list1":["x","y"]}', 
         '{"json_char":"beta", "json_list1":["x","y","z"], "json_list2":["a","b","c"]}'))

期望的结果:

  df <- tibble::tibble(index = list(1, 2),
        json_char = list("alpha", "beta"),
        json_list1 = list(list("x","y"), list("x","y","z")),
        json_list2 = list(NA, list("a","b","c")))

经过大量的实验,我有了这个功能:

extract_json_column <- function(df) {
  df %>%
    magrittr::use_series(data) %>% 
    purrr::map(jsonlite::fromJSON) %>% 
    purrr::map(purrr::simplify) %>% 
    tibble::enframe() %>% 
    tidyr::spread("name", "value") %>%
    purrr::flatten_dfr()
}

这给了我以下错误:Error in bind_rows_(x, .id) : Argument 2 must be length 3, not 7

第一行设置其余数据帧的参数数量。反正有没有避免这种行为?

1 个答案:

答案 0 :(得分:0)

我将您的功能修改为以下内容。我希望这会有所帮助。

library(tidyverse)
library(rjson)

extract_json_column <- function(df){
  df %>%
    rowwise() %>%
    mutate(data = map(data, fromJSON)) %>%
    split(.$index) %>%
    map(~.$data[[1]]) %>%
    map(~map_if(., function(x) length(x) != 1, list)) %>%
    map(as_data_frame) %>%
    bind_rows(.id = "index")
}

extract_json_column(df)
# A tibble: 2 x 4
  index json_char json_list1 json_list2
  <chr>     <chr>     <list>     <list>
1     1     alpha  <chr [2]>     <NULL>
2     2      beta  <chr [3]>  <chr [3]>