Вопрос:

Преобразовать вложенную карту Json в пары ключ-значение

groovy

27 просмотра

3 ответа

28 Репутация автора

У меня есть скрипт, который выбирает данные JSON из URL и анализирует их для сопоставления

Я хочу преобразовать вложенную карту в пары «один ключ-значение». Например:

{
    "glossary": {
        "title": "example glossary",
        "GlossDiv": {
                "title": "S",
        }
    }
}

к

{
    "glossary_title":  "example glossary",
    "glossary_GlossDiv_title": "S"
}

Это код, который мне сейчас нужен для получения данных JSON.

import groovy.json.JsonSlurper

String urlString = "https://pastebin.com/raw/SkACvctU"

def parsedJson = new JsonSlurper().parse(urlString.toURL())

println parsedJson
Автор: Xameer Источник Размещён: 12.06.2019 02:59

Ответы (3)


0 плюса

28 Репутация автора

Я написал рекурсивную функцию для обхода JSON и создания Singular Map. Ниже приведена полная функция для преобразования вложенной карты в единственную карту.

import groovy.json.JsonSlurper
String urlString = "https://pastebin.com/raw/DAGee5Ad"
def parsedJson = new JsonSlurper().parse(urlString.toURL())

Map<String, String> result = new LinkedHashMap();
public void toMap(Object json, String key, Map result){

    json = [(key): json]

    json.each {k, v ->
      if( v instanceof Map ){
        v.each { k1, v1 -> 
            if (v1 instanceof Map)
                toMap(v1, k + "_" + k1 , result)
            else if(v1 instanceof List){
                def count = 1
                v1.each{ v2 ->
                    toMap(v2, k + k1 + count.toString(), result)
                    count = count + 1
                }
            }
            else
                result.put(k + "_" + k1, v1)
        }
      }
    }
}

//Calling the function 
toMap(parsedJson, "json", result)

//Printing the result
result.each{ k, v ->
    println "${k}: ${v}"
}

Выход:

json_glossary_title: example glossary
json_glossary_GlossDiv_title: S
json_glossary_GlossDiv_GlossList_GlossEntry_ID: SGML
json_glossary_GlossDiv_GlossList_GlossEntry_SortAs: SGML
json_glossary_GlossDiv_GlossList_GlossEntry_GlossTerm: Standard Generalized Markup Language
json_glossary_GlossDiv_GlossList_GlossEntry_Acronym: SGML
json_glossary_GlossDiv_GlossList_GlossEntry_Abbrev: ISO 8879:1986
json_glossary_GlossDiv_GlossList_GlossEntry_GlossDef_para: A meta-markup language, used to create markup languages such as DocBook.
json_glossary_GlossDiv_GlossList_GlossEntry_GlossSee: markup
Автор: Xameer Размещён: 12.06.2019 07:12

0 плюса

1 Репутация автора

Вот код для преобразования:

def json = '{' +
            '    "glossary": {' +
            '        "title": "example glossary",' +
            '        "GlossDiv": {' +
            '                "title": "S",' +
            '        }' +
            '    }' +
            '}'


    def jsonSlurper = new JsonSlurper()
    def parsed = jsonSlurper.parseText(json)

    def title = parsed.glossary.title
    def divTitle = parsed.glossary.GlossDiv.title

    def map = ["glossary_title":title, "glossary_GlossDiv_title":divTitle]
    println JsonOutput.toJson(map)
Автор: M. Hossein Amerkashi Размещён: 12.06.2019 05:08

0 плюса

136675 Репутация автора

Вы можете использовать полиморфизм, чтобы получить другое рекурсивное решение:

import groovy.json.JsonSlurper

String urlString = "https://pastebin.com/raw/DAGee5Ad"

def parsedJson = new JsonSlurper().parse(urlString.toURL())

def flatten(Map value, List<String> prefix = []) {

   value.collectEntries { k, v ->
      flatten(v, prefix + k)
   }
}

def flatten(List value, List<String> prefix = []) {
   value.indexed().collectEntries { i, v ->
       flatten(v, prefix + i)
   }
}

def flatten(Object value, List<String> prefix = []) {
   [(prefix.join('_')): value]
}

flatten(parsedJson).each { println it }

Который печатает более полный:

glossary_title=example glossary
glossary_GlossDiv_title=S
glossary_GlossDiv_GlossList_GlossEntry_ID=SGML
glossary_GlossDiv_GlossList_GlossEntry_SortAs=SGML
glossary_GlossDiv_GlossList_GlossEntry_GlossTerm=Standard Generalized Markup Language
glossary_GlossDiv_GlossList_GlossEntry_Acronym=SGML
glossary_GlossDiv_GlossList_GlossEntry_Abbrev=ISO 8879:1986
glossary_GlossDiv_GlossList_GlossEntry_GlossDef_para=A meta-markup language, used to create markup languages such as DocBook.
glossary_GlossDiv_GlossList_GlossEntry_GlossDef_GlossSeeAlso_0_host1=GML
glossary_GlossDiv_GlossList_GlossEntry_GlossDef_GlossSeeAlso_0_host2=XML
glossary_GlossDiv_GlossList_GlossEntry_GlossSee=markup
Автор: tim_yates Размещён: 12.06.2019 06:12
Вопросы из категории :
32x32