Return Nested Key in Groovy

橙三吉。 提交于 2019-12-08 03:52:57

问题


I am trying to determine the best way to return nested key values using groovy. If I have a map:

def map = [
   OrganizationName: 'SampleTest',
   Address: [
      Street: '123 Sample St',
      PostalCode: '00000',
   ]
]

Is there a way to return all of the keys? OrganizationName, OrganizationURL, Address.Street, Address.PostalCode? If I didn't have an map within a map I could use map.keySet() as String[]. Should I just loop through each key and see if it is an instanceof another map?


回答1:


There's no such method You're looking for in groovy. You need to do it using instanceof and probably a recursive method.




回答2:


The Groovy libraries don't provide a method for this, but you can write your own. Here's an example that you can copy-paste into the Groovy console

List<String> getNestedMapKeys(Map map, String keyPrefix = '') {
  def result = []

  map.each { key, value ->
    if (value instanceof Map) {
      result += getNestedMapKeys(value, keyPrefix += "$key.")
    } else {
      result << "$keyPrefix$key"
    }
  }

  result
}

// test it out
def map = [
   OrganizationName: 'SampleTest',
   Address: [
      Street: '123 Sample St',
      PostalCode: '00000',
   ]
]

assert ['OrganizationName', 'Address.Street', 'Address.PostalCode'] == getNestedMapKeys(map)



回答3:


Use Following generic recursion Method To generate the list of all nested map keys

def getListOfKeys(def map, String prefix,def listOfKeys){
    if(map instanceof Map){

        map.each { key, value->
            if(prefix.isEmpty()){
                listOfKeys<<key
            }else{
                listOfKeys<< prefix+"."+key
            }

            if(value instanceof List){

                List list = value

                list.eachWithIndex { item, index ->
                    if(prefix.isEmpty()){
                        getListOfKeys(item, key+"["+index+"]",listOfKeys)
                    }else{
                        getListOfKeys(item, prefix+"."+key+"["+index+"]",listOfKeys)
                    }
                }

            }else if(value instanceof Map){

                if(prefix.isEmpty()){
                    getListOfKeys(value, key,listOfKeys)
                }else{
                    getListOfKeys(value, prefix+"."+key,listOfKeys)
                }

            }
        }
    }
}

call above method as follows

  def void findAllKeysInMap(){

    Map map =   [ "fields":[
            "project":
            [
                "key": "TP"
            ],
            "summary": "Api Testing Issue.",
            "description": "This issue is only for api testing purpose",
            "issuetype": [
                "name": ["Bug":["hello":[["saurabh":"gaur","om":"prakash"],                      ["gaurav":"pandey"], ["mukesh":"mishra"]]]]
            ]
        ]
    ]

            def listOfKeys=[]

            getListOfKeys(map, '', listOfKeys)

            println "listOfKeys>>>"+listOfKeys
         }

output: listOfKeys>>>[fields, fields.project, fields.project.key, fields.summary, fields.description, fields.issuetype, fields.issuetype.name, fields.issuetype.name.Bug, fields.issuetype.name.Bug.hello, fields.issuetype.name.Bug.hello[0].saurabh, fields.issuetype.name.Bug.hello[0].om, fields.issuetype.name.Bug.hello[1].gaurav, fields.issuetype.name.Bug.hello[2].mukesh]




回答4:


Slightly shorter:

String key = 'Address.Street'
key.split('\\.').inject(yourMap) {map, path -> map[path]}

If you can't guarantee that the path exists and is complete (say, if you tried to access OrganizationName.id) you'll need to add some safeguards (check that map is not null, and that it's really a Map)



来源:https://stackoverflow.com/questions/25916607/return-nested-key-in-groovy

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!