Вот некоторые дополнительные разъяснения
Для объекта ввода {"key1":1, "key2":2, "key3":3}
хотелось бы удалить все ключи, которых нет в наборе нужных ключей ["key1","key3","key4"]
jq -n --argjson desired_keys '["key1","key3","key4"]' \
--argjson input '{"key1":1, "key2":2, "key3":3}' \
' $input
| with_entries(
select(
.key == ($desired_keys[])
)
)'
with_entries
преобразует {"key1":1, "key2":2, "key3":3}
в следующий массив пар ключ-значение и сопоставляет оператор select с массивом, а затем превращает полученный массив обратно в объект.
Вот внутренний объект в операторе with_entries
.
[
{
"key": "key1",
"value": 1
},
{
"key": "key2",
"value": 2
},
{
"key": "key3",
"value": 3
}
]
затем мы можем выбрать ключи из этого массива, которые соответствуют нашим критериям.
Вот где происходит волшебство... вот посмотрите, что происходит в середине этой команды. Следующая команда берет расширенный массив значений и превращает их в список объектов, из которых мы можем выбирать.
jq -cn '{"key":"key1","value":1}, {"key":"key2","value":2}, {"key":"key3","value":3}
| select(.key == ("key1", "key3", "key4"))'
Это даст следующий результат
{"key":"key1","value":1}
{"key":"key3","value":3}
Команда с записями может быть немного сложной, но легко запомнить, что она использует фильтр и определяется следующим образом.
def with_entries(f): to_entries|map(f)|from_entries;
Это то же самое, что
def with_entries(f): [to_entries[] | f] | from_entries;
Другая часть вопроса, которая смущает людей, — это множественные совпадения справа от ==
.
Рассмотрим следующую команду. Мы видим, что на выходе получается внешнее произведение всех левых и правых списков.
jq -cn '1,2,3| . == (1,1,3)'
true
true
false
false
false
false
false
false
true
Если этот предикат находится в операторе выбора, мы сохраняем ввод, когда предикат истинен. Обратите внимание, что здесь вы также можете дублировать входные данные.
jq -cn '1,2,3| select(. == (1,1,3))'
1
1
3
person
Jon
schedule
11.04.2017
select(.key == ("1","3","4"))
- person Jon   schedule 15.06.2015