оптимистичную код, который я мог придумать:
def map3 = [map1, map2].transpose()*.sum().each { m ->
m.balance = m.quota - m.copiesToDate
}
редактирования: как отмечает Тим, этот код работает до тех пор, как два входных списков (map1 и map2) одного и того же размера и иметь карты в порядке. Если это не так, я бы порекомендовал ответ Тима, который обрабатывает эти случаи.
Приведенное выше возвращает карту, определенную в вашем вопросе. Следующий код:
def list1 = [
[name: 'Coord1', quota: 200],
[name: 'Coord2', quota: 300]
]
def list2 = [
[name: 'Coord1', copiesToDate: 60],
[name: 'Coord2', copiesToDate: 30]
]
def x = [list1, list2].transpose()*.sum().each { m ->
m.balance = m.quota - m.copiesToDate
}
x.each {
println it
}
демонстрирует идею и печатает:
[name:Coord1, quota:200, copiesToDate:60, balance:140]
[name:Coord2, quota:300, copiesToDate:30, balance:270]
Я переименованный map1
и map2
в list1
и list2
, так как они на самом деле два списка, содержащих внутренние карты.
Код несколько кратким и может потребоваться немного пояснения, если вы не используете transpose
и операции с разворотом и картографией.
Объяснение:
[list1, list2]
- сначала создать новый список, в котором две существующие списки элементов. Итак, теперь у нас есть список списков, в которых элементы во внутренних списках являются картами.
.transpose()
- тогда мы вызываем transpose, которому может потребоваться немного усилий, чтобы понять, когда вы видите его в первый раз. Если у вас есть список списков, вы можете увидеть транспонирование, перелистывая списки «в другое направление».
В нашем случае два списка:
[[name:Coord1, quota:200], [name:Coord2, quota:300]]
[[name:Coord1, copiesToDate:60], [name:Coord2, copiesToDate:30]]
стал:
[[name:Coord1, quota:200], [name:Coord1, copiesToDate:60]]
[[name:Coord2, quota:300], [name:Coord2, copiesToDate:30]]
т.е. после того, как транспонирования, все, что касается Coord1 в первом списке, и все, что касается Coord2 находится в второй.
- Каждый из списков, которые мы имеем сейчас, представляет собой список карт. Но мы хотим только одну карту для Coord1 и одну карту для Coord2. Поэтому для каждого из приведенных выше списков нам нужно объединить или объединить содержащиеся карты в одну карту. Мы делаем это, используя тот факт, что в карте groovy + map возвращается объединенная карта.Используя , мы поэтому вызываем
sum()
в каждый список карт.
т.е .:
[[name:Coord1, quota:200], [name:Coord1, copiesToDate:60]].sum()
вычисляет в:
[name:Coord1, quota:200, copiesToDate:60]
и:
[[name:Coord2, quota:300], [name:Coord2, copiesToDate:30]].sum()
в:
[name:Coord2, quota:300, copiesToDate:30]
- Наконец, мы хотим добавить к картам свойство
balance
, чтобы мы перебирали то, что теперь представляет собой список двух карт, и добавляем баланс в качестве вычисления квоты - copyToDate. Конструкция each
возвращает список, в котором он работает, и который мы назначаем x.
Transpose опирается на списки, имеющие одинаковый порядок, без недостающих элементов в каждом из них –
True. Поэтому для списков разной длины или порядка вам придется делать что-то еще. Оператор явно указал, что карты имеют одинаковый размер, который я выбрал для чтения, поскольку списки имеют одинаковый размер:). Для смены порядка вы наиболее корректны, транспонирование не будет работать. –