使用 jq 对数组中的元素对进行分组的最简洁方法
Most concise way to group pairs of elements in an array with jq
我要转换
[1,"a",2,"b",3,"c"]
到
[[1,"a"],[2,"b"],[3,"c"]]
我想到的最好的是(使用 1.5)
[recurse(.[2:];length>1)[0:2]]
我可以使用更简洁或更高效或兼容 1.4 的解决方案吗?
就我个人而言,我会尝试像您那样做一些事情,从功能的角度来看,对我来说感觉是正确的。
但是还有其他表达方式。您可以利用这样一个事实,即在将数组转换为条目时,您会得到一个 index/value 对数组。
to_entries | group_by(.key/2 | floor) | map(map(.value))
另一方面,您也可以只使用一系列数字创建数组的切片。我认为这可能比递归表现更好。
. as $arr | [ range(0; length/2) * 2 | $arr[.:.+2] ]
以下概括了任务,适用于 jq 1.4,在 jq 1.5 中的优化具有很高的性能,可用于实现 rho/1(如 R 的 "dim(z) <- c(3,5,100)" 和 APL 的 "A⍴B"):
# Input: an array
# Output: a stream of arrays
# If the input is [] then the output stream is empty,
# otherwise it consists of arrays of length n, each array consisting
# of successive elements from the input array, padded with nulls.
def takes(n):
def _takes:
if length == 0 then empty
elif length < n then .[n-1] = null
else .[0:n], (.[n:] | _takes)
end;
_takes;
使用 "takes",可以使用以下方法完成任务:[takes(2)]
使用"rho",有几种可能性,特别是:
[rho( [ 2 ] )]
# or:
rho([3,2])
有关 "rho" 的更多信息,请参阅 https://github.com/stedolan/jq/issues/829
也许不是最简洁的方法,但这是使用 foreach 收集和发出值对的解决方案。
[
foreach .[] as $x (
[] # init
; if length>1 then [] else . end # update
| . + [$x]
; if length>1 then . else empty end # extract
)
]
我要转换
[1,"a",2,"b",3,"c"]
到
[[1,"a"],[2,"b"],[3,"c"]]
我想到的最好的是(使用 1.5)
[recurse(.[2:];length>1)[0:2]]
我可以使用更简洁或更高效或兼容 1.4 的解决方案吗?
就我个人而言,我会尝试像您那样做一些事情,从功能的角度来看,对我来说感觉是正确的。
但是还有其他表达方式。您可以利用这样一个事实,即在将数组转换为条目时,您会得到一个 index/value 对数组。
to_entries | group_by(.key/2 | floor) | map(map(.value))
另一方面,您也可以只使用一系列数字创建数组的切片。我认为这可能比递归表现更好。
. as $arr | [ range(0; length/2) * 2 | $arr[.:.+2] ]
以下概括了任务,适用于 jq 1.4,在 jq 1.5 中的优化具有很高的性能,可用于实现 rho/1(如 R 的 "dim(z) <- c(3,5,100)" 和 APL 的 "A⍴B"):
# Input: an array
# Output: a stream of arrays
# If the input is [] then the output stream is empty,
# otherwise it consists of arrays of length n, each array consisting
# of successive elements from the input array, padded with nulls.
def takes(n):
def _takes:
if length == 0 then empty
elif length < n then .[n-1] = null
else .[0:n], (.[n:] | _takes)
end;
_takes;
使用 "takes",可以使用以下方法完成任务:[takes(2)]
使用"rho",有几种可能性,特别是:
[rho( [ 2 ] )]
# or:
rho([3,2])
有关 "rho" 的更多信息,请参阅 https://github.com/stedolan/jq/issues/829
也许不是最简洁的方法,但这是使用 foreach 收集和发出值对的解决方案。
[
foreach .[] as $x (
[] # init
; if length>1 then [] else . end # update
| . + [$x]
; if length>1 then . else empty end # extract
)
]