考虑给予JSON
{
"data": {
"array": [
{
"foo": {"a": "1 foo a", "b": "2 foo b", "c": 512},
"bar": {"a": "3 bar a", "b": "4 bar b"},
"baz": {"a": "5 baz a", "b": "6 baz b", "d": 75},
"other": {"a": 2, "x": 13, "y": 44},
},
{
"foo": {"a": "7 foo a", "b": "8 foo b"},
"bar": {"a": "9 bar a", "b": "10 bar b"},
"baz": {"a": "11 baz a", "b": "12 baz b"},
"other": {"a": 2, "x": 13, "y": 44, "z": 132},
}
]
}
}使用简单的JSONPath,我可以按各自的顺序列出foos、bars和bazes中的所有foos和bs。
$.data.array[*][foo,bar,baz][a,b][
"1 foo a", "2 foo b",
"3 bar a", "4 bar b",
"5 baz a", "6 baz b",
"7 foo a", "8 foo b",
"9 bar a", "10 bar b",
"11 baz a", "12 baz b"
]有使用Groovy GPath的方法吗?我想出的唯一可行的解决方案是:
def json = new JsonSlurper().parseText(jsonText)
json.data.array.foo.a
+ json.data.array.foo.b
+ json.data.array.bar.a
+ json.data.array.bar.b
+ json.data.array.baz.a
+ json.data.array.baz.b但是结果仍然与JSONPath不同(顺序)
[1 foo a, 7 foo a,
2 foo b, 8 foo b,
3 bar a, 9 bar a,
4 bar b, 10 bar b,
5 baz a, 11 baz a,
6 baz b, 12 baz b]附注:
我正在使用GPath进行我的放心测试,所以如果有其他方法来获得同样的结果,我会很高兴看到它。
P.P.S
实际上我找到了另一个解决方案
json.data.array
*.subMap(["foo", "bar", "baz"])*.values().flatten()
*.subMap(["a", "b"])*.values().flatten()产生与JSONPath相同的结果。
[1 foo a, 2 foo b,
3 bar a, 4 bar b,
5 baz a, 6 baz b,
7 foo a, 8 foo b,
9 bar a, 10 bar b,
11 baz a, 12 baz b]但在JSONPath,它仍然不是工会运作的替代方案。例如,还有另一个更复杂的表达式:
$.data.array[*][foo,bar,?(@.a == '11 baz a')][a,b]GPath的替代方案与上面的subMap解决方案完全不同。
发布于 2022-05-19 09:37:58
多亏了@肖,我找到了最接近JsonPath的解决方案:
def json = new JsonSlurper().parseText(input) //text is your json string
def result = json.data.array
.collectMany { [it.foo, it.bar, it.baz] }
.collectMany { [it.a, it.b] }
println result // [1 foo a, 2 foo b, 3 bar a, 4 bar b, 5 baz a, 6 baz b, 7 foo a, 8 foo b, 9 bar a, 10 bar b, 11 baz a, 12 baz b]但是,如果我想要替代
$.data.array[*][foo,bar,?(@.a == '11 baz a')][a,b]其结果是更加肮脏:
def result = json.data.array
.collectMany {
[it.foo, it.bar] + (it.baz.a == '11 baz a' ? it.baz : [])
}
.collectMany { [it.a, it.b] }我认为,如果我们忽略了使用过滤器,collectMany可以被视为等同于[,]。
欢迎您的过滤联盟版本。
发布于 2022-05-14 13:19:59
下面是使用collectMany和收集方法解决问题的纯gpath版本:
根据RomanMitasov最新问题的最新答复:
def json = new JsonSlurper().parseText(text) //text is your json string
def result = json.data.array*.collectMany{k,v-> k in ["foo","bar","baz"]? v.collect{k1,v1-> k1 in ["a","b"]? v1:[]}:[]}.flatten()
println result //[1 foo a, 2 foo b, 3 bar a, 4 bar b, 5 baz a, 6 baz b, 7 foo a, 8 foo b, 9 bar a, 10 bar b, 11 baz a, 12 baz b]原来的答案:
def json = new JsonSlurper().parseText(text) //text is your json string
def result = json.data.array*.collectMany{k,v->v.collect{it.value}}.flatten()
println result //[1 foo a, 2 foo b, 3 bar a, 4 bar b, 5 baz a, 6 baz b, 7 foo a, 8 foo b, 9 bar a, 10 bar b, 11 baz a, 12 baz b]https://stackoverflow.com/questions/71726821
复制相似问题