Reputation: 3773
I am trying to filter my list based on the below condition.
check if any records with duplicate name
and employee
fields. If it has duplicates then keep only the element whose date
field value is latest and ignoring other duplicate values.
input list:
[{
name: "Bob",
employee: "yes",
date: "10/12/2020"
},
{
name: "John",
employee: "no",
date: "14/12/2020"
},
{
name: "Bob",
employee: "yes",
date: "14/12/2020"
},
{
name: "Doe",
employess: "yes",
date: "10/01/2020"
},
{
name: "Bob",
employess: "yes",
date: "09/12/2020"
},
{
name: "Doe",
employee: "yes",
date: "01/12/2019"
},
{
name: "Bob",
employee: "no",
date: "01/12/2019"
}]
Desirable output:
[{
name: "Bob",
employee: "yes",
date: "14/12/2020"
},
{
name: "John",
employee: "no",
date: "14/12/2020"
},
{
name: "Bob",
employee: "no",
date: "01/12/2019"
},
{
name: "Doe",
employess: "yes",
date: "10/01/2020"
}]
I tried with findAll()
method but not able to get desired results.
Upvotes: 0
Views: 59
Reputation: 37033
You can groupBy
the sub map of name
and employee
and then find the
max date
in the values of the grouped items. E.g.
def data = [
[a: 1, b: 2, c: 0],
[a: 1, b: 2, c: 3],
[a: 2, b: 3, c: 0],
]
data.groupBy{
it.subMap(["a", "b"])
}.collect{ k, v ->
k + [c: v*.c.max()]
}
// -> [[a:1, b:2, c:3], [a:2, b:3, c:0]]
Upvotes: 2
Reputation: 20699
A simple inject
would help:
def list = [[
name: "Bob",
employee: "yes",
date: "10/12/2020"
],
[
name: "John",
employee: "no",
date: "14/12/2020"
],
[
name: "Bob",
employee: "yes",
date: "14/12/2020"
],
[
name: "Doe",
employee: "yes",
date: "10/01/2020"
],
[
name: "Bob",
employee: "yes",
date: "09/12/2020"
],
[
name: "Doe",
employee: "yes",
date: "01/12/2019"
],
[
name: "Bob",
employee: "no",
date: "01/12/2019"
]]
def sdf = new java.text.SimpleDateFormat('dd/MM/yyyy')
def result = list.inject( [:] ){ res, curr ->
Date date = sdf.parse curr.date
String key = curr.name + '_' + curr.employee
if( res[ key ]?.date < date ){
res[ key ] = curr + [ date:date ]
}
res
}.values().collect{ it + [ date:sdf.format( it.date ) ] }.join('\n')
println result
prints
[name:Bob, employee:yes, date:14/12/2020]
[name:John, employee:no, date:14/12/2020]
[name:Doe, employee:yes, date:10/01/2020]
[name:Bob, employee:no, date:01/12/2019]
Upvotes: 1
Reputation: 115
As an option, you can collect the initial list as nested maps. For example, first you can group records by name. Then group by an employee. Eventually, you will get the following Map<String, Map<String, List>. Now you can fetch a record by keys in maps and the latest date in the list.
Upvotes: 0