json - 通过 {} 压缩 jq 对象构造中的列表,而不是像默认那样将它们相乘

标签 json jq transpose

像这样的 JSON 对象:

{"user":"stedolan","titles":["JQ Primer", "More JQ"],"years":[2013, 2016]}

而且,我想将其转换为压缩列表(假设所有列表的长度 N)并像这样输出:

{"user":"stedolan","title":"JQ Primer","year":2013}
{"user":"stedolan","title":"More JQ","year":2016}

我遵循 Object -{} 示例并尝试:

tmp='{"user":"stedolan","titles":["JQ Primer", "More JQ"],"years":[2013, 2016]}'
echo $tmp | jq '{user, title: .titles[], year: .years[]}'

然后输出:

{"user":"stedolan","title":"JQ Primer","year":2013}
{"user":"stedolan","title":"JQ Primer","year":2016}
{"user":"stedolan","title":"More JQ","year":2013}
{"user":"stedolan","title":"More JQ","year":2016}

它产生 N*N ... 行结果,而不是 N 行结果。

欢迎任何建议!

最佳答案

transpose/0 可用于有效地将值压缩在一起。赋值工作方式的好处在于它可以同时赋值给多个变量。

([.titles,.years]|transpose[]) as [$title,$year] | {user,$title,$year}

如果您希望将结果放在数组而不是流中,只需将其全部包装在 [] 中即可。

https://jqplay.org/s/ZIFU5gBnZ7


对于 jq 1.4 兼容版本,您必须重写它以不使用解构,但您可以使用来自内置函数的相同 transpose/0 实现。

transpose/0 :

def transpose:
  if . == [] then []
  else . as $in
  | (map(length) | max) as $max
  | length as $length
  | reduce range(0; $max) as $j
      ([]; . + [reduce range(0;$length) as $i ([]; . + [ $in[$i][$j] ] )] )
            end;

这是我编写的替代实现,它也应该兼容。 :)

def transpose2:
    length as $cols
      | (map(length) | max) as $rows
      | [range(0;$rows) as $r | [.[range(0;$cols)][$r]]];
([.titles,.years]|transpose[]) as $p | {user,title:$p[0],year:$p[1]}

关于json - 通过 {} 压缩 jq 对象构造中的列表,而不是像默认那样将它们相乘,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57283364/

相关文章:

javascript - 使用 JS 从 Solr 获取 JSONfacet_queries

javascript - 通过添加key修改Json结果

java - JSONObject 在使用字符串实例化后返回非空值 "null"

javascript - 使用jq将子属性分配给父字典

sql - Hive SQL 中的转置/透视表

c++ - json写组合?

json - 无法在 linux 中使用 jq 解析 artifactory 的 json 输出

bash - jq - 像数组一样遍历 bash 中的对象(aws 卷)

pandas - 转置数据框后的列名称

python - Pandas 中的列到行