使用 jq 将 bash-array 写入 json:每个对象一个元素
write bash-array to json with jq: one element per object
我正在尝试将 bash 数组中的一些值保存到现有的 json 中。我尝试了一些不同的方法,但未能解决问题。我在这里错过了什么?
input.json
{
"type": "FeatureCollection",
"name": "test",
"features": [
{ "type": "Feature", "properties": { "OBJECTID": 3213, "USE": "dem", "tile": "4045644"}},
{ "type": "Feature", "properties": { "OBJECTID": 3214, "USE": "dem", "tile": "4045646"}},
{ "type": "Feature", "properties": { "OBJECTID": 3215, "USE": "dem", "tile": "4045648"}}
]
}
Bash 中某些计算的输出 - 100% 来自 input.json。所以这个数组长度 == input.json
中“features[]”数组的长度
printf '%s\n' "${pushintojson[@]}"
4045646 NV NV NV
4045648 NV 4045644 NV
4045650 NV 4045646 NV
jq '.features |= map(.properties += {NOSW: $ARGS.positional})' --args "${pushintojson[@]}" <<< "${input.json}"
所以这会产生这个(我为便于阅读而添加的换行符):
{
"type":"FeatureCollection",
"name":"test",
"features": [
{"type":"Feature","properties":{"OBJECTID":3213,"USE":"dem","tile":"4045644",
"NOSW":[
"4045646 NV NV NV",
"4045648 NV 4045644 NV",
"4045650 NV 4045646 NV"
]}},
{"type":"Feature","properties":{"OBJECTID":3214,"USE":"dem","tile":"4045646",
"NOSW":[
"4045646 NV NV NV",
"4045648 NV 4045644 NV",
"4045650 NV 4045646 NV"
]}},
{"type":"Feature","properties":{"OBJECTID":3215,"USE":"dem","tile":"4045648",
"NOSW":[
"4045646 NV NV NV",
"4045648 NV 4045644 NV",
"4045650 NV 4045646 NV"
]}}
]
}
bash 数组的所有值都保存到每个元素。每个 json-object 应该只有一个值——实际上是一个数组本身。
所以在伪:“pushintojson[0]”需要在“features[0]”下,pushintojson[1]”到“features[1]”
pushintojson[2]”到“features[2]”等等
期望的输出
{
"type":"FeatureCollection",
"name":"test",
"features": [
{"type":"Feature","properties":{"OBJECTID":3213,"USE":"dem","tile":"4045644",
"NOSW":"4045646 NV NV NV"
}},
{"type":"Feature","properties":{"OBJECTID":3214,"USE":"dem","tile":"4045646",
"NOSW":"4045648 NV 4045644 NV"
}},
{"type":"Feature","properties":{"OBJECTID":3215,"USE":"dem","tile":"4045648",
"NOSW":"4045650 NV 4045646 NV"
}}
]
}
如果您只使用 map
,那么对于每个元素,您最终都会再次遍历所有参数。相反,您必须将 .features
数组与 $ARGS.positional
数组对齐。
一种更接近您尝试的方法是使用 to_entries
扩展 .features
数组,使数组的元素与其键匹配,而键又可以在 [=13] 中使用=] 通过索引引用 $ARGS.positional
数组的相应项。
jq '
.features |= (to_entries | map(
.value * {properties: {NOSW: $ARGS.positional[.key]}}
))
' --args "${pushintojson[@]}" < input.json
另一种方法是使用 transpose
从两个初始数组生成一个对齐项目的数组,然后再次 map
它们的内容在一起。
jq '
.features |= ([., $ARGS.positional] | transpose | map(
.[0] * {properties: {NOSW: .[1]}}
))
' --args "${pushintojson[@]}" < input.json
两者都产生
{
"type": "FeatureCollection",
"name": "test",
"features": [
{
"type": "Feature",
"properties": {
"OBJECTID": 3213,
"USE": "dem",
"tile": "4045644",
"NOSW": "4045646 NV NV NV"
}
},
{
"type": "Feature",
"properties": {
"OBJECTID": 3214,
"USE": "dem",
"tile": "4045646",
"NOSW": "4045648 NV 4045644 NV"
}
},
{
"type": "Feature",
"properties": {
"OBJECTID": 3215,
"USE": "dem",
"tile": "4045648",
"NOSW": "4045650 NV 4045646 NV"
}
}
]
}
我正在尝试将 bash 数组中的一些值保存到现有的 json 中。我尝试了一些不同的方法,但未能解决问题。我在这里错过了什么?
input.json
{
"type": "FeatureCollection",
"name": "test",
"features": [
{ "type": "Feature", "properties": { "OBJECTID": 3213, "USE": "dem", "tile": "4045644"}},
{ "type": "Feature", "properties": { "OBJECTID": 3214, "USE": "dem", "tile": "4045646"}},
{ "type": "Feature", "properties": { "OBJECTID": 3215, "USE": "dem", "tile": "4045648"}}
]
}
Bash 中某些计算的输出 - 100% 来自 input.json。所以这个数组长度 == input.json
中“features[]”数组的长度printf '%s\n' "${pushintojson[@]}"
4045646 NV NV NV
4045648 NV 4045644 NV
4045650 NV 4045646 NV
jq '.features |= map(.properties += {NOSW: $ARGS.positional})' --args "${pushintojson[@]}" <<< "${input.json}"
所以这会产生这个(我为便于阅读而添加的换行符):
{
"type":"FeatureCollection",
"name":"test",
"features": [
{"type":"Feature","properties":{"OBJECTID":3213,"USE":"dem","tile":"4045644",
"NOSW":[
"4045646 NV NV NV",
"4045648 NV 4045644 NV",
"4045650 NV 4045646 NV"
]}},
{"type":"Feature","properties":{"OBJECTID":3214,"USE":"dem","tile":"4045646",
"NOSW":[
"4045646 NV NV NV",
"4045648 NV 4045644 NV",
"4045650 NV 4045646 NV"
]}},
{"type":"Feature","properties":{"OBJECTID":3215,"USE":"dem","tile":"4045648",
"NOSW":[
"4045646 NV NV NV",
"4045648 NV 4045644 NV",
"4045650 NV 4045646 NV"
]}}
]
}
bash 数组的所有值都保存到每个元素。每个 json-object 应该只有一个值——实际上是一个数组本身。 所以在伪:“pushintojson[0]”需要在“features[0]”下,pushintojson[1]”到“features[1]” pushintojson[2]”到“features[2]”等等
期望的输出
{
"type":"FeatureCollection",
"name":"test",
"features": [
{"type":"Feature","properties":{"OBJECTID":3213,"USE":"dem","tile":"4045644",
"NOSW":"4045646 NV NV NV"
}},
{"type":"Feature","properties":{"OBJECTID":3214,"USE":"dem","tile":"4045646",
"NOSW":"4045648 NV 4045644 NV"
}},
{"type":"Feature","properties":{"OBJECTID":3215,"USE":"dem","tile":"4045648",
"NOSW":"4045650 NV 4045646 NV"
}}
]
}
如果您只使用 map
,那么对于每个元素,您最终都会再次遍历所有参数。相反,您必须将 .features
数组与 $ARGS.positional
数组对齐。
一种更接近您尝试的方法是使用 to_entries
扩展 .features
数组,使数组的元素与其键匹配,而键又可以在 [=13] 中使用=] 通过索引引用 $ARGS.positional
数组的相应项。
jq '
.features |= (to_entries | map(
.value * {properties: {NOSW: $ARGS.positional[.key]}}
))
' --args "${pushintojson[@]}" < input.json
另一种方法是使用 transpose
从两个初始数组生成一个对齐项目的数组,然后再次 map
它们的内容在一起。
jq '
.features |= ([., $ARGS.positional] | transpose | map(
.[0] * {properties: {NOSW: .[1]}}
))
' --args "${pushintojson[@]}" < input.json
两者都产生
{
"type": "FeatureCollection",
"name": "test",
"features": [
{
"type": "Feature",
"properties": {
"OBJECTID": 3213,
"USE": "dem",
"tile": "4045644",
"NOSW": "4045646 NV NV NV"
}
},
{
"type": "Feature",
"properties": {
"OBJECTID": 3214,
"USE": "dem",
"tile": "4045646",
"NOSW": "4045648 NV 4045644 NV"
}
},
{
"type": "Feature",
"properties": {
"OBJECTID": 3215,
"USE": "dem",
"tile": "4045648",
"NOSW": "4045650 NV 4045646 NV"
}
}
]
}