假设我们有一个带有一堆键的对象,并希望其中一些键以特定顺序出现,而其他键保持原样。然后可以使用以下示例说明的技术:
$ jq -n '{a:2,b:3,first:0,second:1} | . as $in | {first,second} + $in'
结果:
{
"first": 0,
"second": 1,
"a": 2,
"b": 3
}
重新生成密钥
让我们将定义键顺序的对象称为“模板对象”(上面的{first,second})。请注意,使用上述技术,“模板对象”中的键始终出现在结果中。如果我们只希望模板对象键出现在输入中时出现在结果中,我们可以使用以下函数修改上述方法:
def rekey(obj):
. as $in
| reduce (obj|keys_unsorted)[] as $k ({};
if $in|has($k) then . + {($k): $in[$k]} else . end)
| . + $in ;
例如:
{a:2,b:3,first:0,second:1} | rekey({first,second,third})
产生:
{
"first": 0,
"second": 1,
"a": 2,
"b": 3
}
与walk/1
如果想要递归地重新排序键,可以使用walk/1(定义为https://github.com/stedolan/jq/blob/master/src/builtin.jq),
如此处所示,使用上述rekey 的定义:
walk(if type == "object" then rekey($template) else . end)
其中 $template 代表“模板对象”。
无需定义walk/1 的特殊变体。只需定义一个函数,该函数将任意对象作为输入,并产生所需的重新排序。
(如果你的jq自带的walk/1版本使用keys,那么你应该考虑更新你的jq,或者重新定义walk/1使用keys_unsorted。)