gpt4 book ai didi

jq 中的 SQL 样式 GROUP BY 聚合函数(COUNT、SUM 等)

转载 作者:行者123 更新时间:2023-12-03 14:11:28 25 4
gpt4 key购买 nike

以前在这里问过类似的问题:

计算单个键的项目:jq count the number of items in json by a specific key

计算对象值的总和:
How do I sum the values in an array of maps in jq?



如何模拟 COUNT 聚合函数,它的行为应该与其 SQL 原始函数类似?让我们进一步扩展这个问题以包括其他常规 SQL 函数:

  • 计数
  • 总和/最大值/最小值/平均值
  • ARRAY_AGG

  • 最后一个不是标准的 SQL 函数——它来自 PostgreSQL 但非常有用。

    输入端是一个有效的 JSON 对象流。为了演示,让我们选择一个关于主人和他们的宠物的简单故事。

    模型和数据

    基础关系: 业主
    id name  age
    1 Adams 25
    2 Baker 55
    3 Clark 40
    4 Davis 31

    基础关系: 宠物
    id name  litter owner_id
    10 Bella 4 1
    20 Lucy 2 1
    30 Daisy 3 2
    40 Molly 4 3
    50 Lola 2 4
    60 Sadie 4 4
    70 Luna 3 4

    来源

    从上面我们得到一个导数关系 Owner_Pet (上述关系的 SQL JOIN 的结果)以 JSON 格式呈现给我们的 jq 查询( 源数据 ):
    { "owner_id": 1, "owner": "Adams", "age": 25, "pet_id": 10, "pet": "Bella", "litter": 4 }
    { "owner_id": 1, "owner": "Adams", "age": 25, "pet_id": 20, "pet": "Lucy", "litter": 2 }
    { "owner_id": 2, "owner": "Baker", "age": 55, "pet_id": 30, "pet": "Daisy", "litter": 3 }
    { "owner_id": 3, "owner": "Clark", "age": 40, "pet_id": 40, "pet": "Molly", "litter": 4 }
    { "owner_id": 4, "owner": "Davis", "age": 31, "pet_id": 50, "pet": "Lola", "litter": 2 }
    { "owner_id": 4, "owner": "Davis", "age": 31, "pet_id": 60, "pet": "Sadie", "litter": 4 }
    { "owner_id": 4, "owner": "Davis", "age": 31, "pet_id": 70, "pet": "Luna", "litter": 3 }

    要求

    以下是示例请求及其预期输出:
  • 计算每个主人的宠物数量:
  • { "owner_id": 1, "owner": "Adams", "age": 25, "pets_count": 2 }
    { "owner_id": 2, "owner": "Baker", "age": 55, "pets_count": 1 }
    { "owner_id": 3, "owner": "Clark", "age": 40, "pets_count": 1 }
    { "owner_id": 4, "owner": "Davis", "age": 31, "pets_count": 3 }
  • 总结每个所有者的幼崽数量 获得他们的最大值(最小值/平均值):
  • { "owner_id": 1, "owner": "Adams", "age": 25, "litter_total": 6, "litter_max": 4 }
    { "owner_id": 2, "owner": "Baker", "age": 55, "litter_total": 3, "litter_max": 3 }
    { "owner_id": 3, "owner": "Clark", "age": 40, "litter_total": 4, "litter_max": 4 }
    { "owner_id": 4, "owner": "Davis", "age": 31, "litter_total": 9, "litter_max": 4 }
  • 每个拥有者的 ARRAY_AGG 宠物:
  • { "owner_id": 1, "owner": "Adams", "age": 25, "pets": [ "Bella", "Lucy" ] }
    { "owner_id": 2, "owner": "Baker", "age": 55, "pets": [ "Daisy" ] }
    { "owner_id": 3, "owner": "Clark", "age": 40, "pets": [ "Molly" ] }
    { "owner_id": 4, "owner": "Davis", "age": 31, "pets": [ "Lola", "Sadie", "Luna" ] }

    最佳答案

    扩展 jq 解决方案:

    定制 count() 功能:

    jq -sc 'def count($k): group_by(.[$k])[] | length as $l | .[0] 
    | .pets_count = $l
    | del(.pet_id, .pet, .litter);
    count("owner_id")' source.data

    输出:
    {"owner_id":1,"owner":"Adams","age":25,"pets_count":2}
    {"owner_id":2,"owner":"Baker","age":55,"pets_count":1}
    {"owner_id":3,"owner":"Clark","age":40,"pets_count":1}
    {"owner_id":4,"owner":"Davis","age":31,"pets_count":3}

    定制 sum() 功能:
    jq -sc 'def sum($k): group_by(.[$k])[] | map(.litter) as $litters | .[0] 
    | . + {litter_total: $litters | add, litter_max: $litters | max}
    | del(.pet_id, .pet, .litter);
    sum("owner_id")' source.data

    输出:
    {"owner_id":1,"owner":"Adams","age":25,"litter_total":6,"litter_max":4}
    {"owner_id":2,"owner":"Baker","age":55,"litter_total":3,"litter_max":3}
    {"owner_id":3,"owner":"Clark","age":40,"litter_total":4,"litter_max":4}
    {"owner_id":4,"owner":"Davis","age":31,"litter_total":9,"litter_max":4}

    定制 array_agg() 功能:
    jq -sc 'def array_agg($k): group_by(.[$k])[] | map(.pet) as $pets | .[0] 
    | .pets = $pets | del(.pet_id, .pet, .litter);
    array_agg("owner_id")' source.data

    输出:
    {"owner_id":1,"owner":"Adams","age":25,"pets":["Bella","Lucy"]}
    {"owner_id":2,"owner":"Baker","age":55,"pets":["Daisy"]}
    {"owner_id":3,"owner":"Clark","age":40,"pets":["Molly"]}
    {"owner_id":4,"owner":"Davis","age":31,"pets":["Lola","Sadie","Luna"]}

    关于jq 中的 SQL 样式 GROUP BY 聚合函数(COUNT、SUM 等),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48321235/

    25 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com