Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Combining lists within a nested list, if lists contain the same element?

I have nested list that has a structure similar to this, except it's obviously much longer:

mylist = [ ["Bob", "12-01 2:30"], ["Sal", "12-01 5:23"], ["Jill", "12-02 1:28"] ]

My goal is to create another nested lists that combines all elements that have the same date. So, the following output is desired:

newlist = [  [["Bob", "12-01 2:30"], ["Sal", "12-01 5:23"]], [["Jill", "12-02 1:28"]]  ]

Above, all items with the date 12-01, regardless of time, are combined, and all elements of 12-02 are combined.

I've sincerely been researching how to do this for the past 1 hour and can't find anything. Furthermore, I'm a beginner at programming, so I'm not skilled enough to try to create my own solution. So, please don't think that I haven't attempted to do research or put any effort into trying this problem myself. I'll add a few links as examples of my research below:

Collect every pair of elements from a list into tuples in Python

Create a list of tuples with adjacent list elements if a condition is true

How do I concatenate two lists in Python?

Concatenating two lists of Strings element wise in Python without Nested for loops

Zip two lists together based on matching date in string

How to merge lists into a list of tuples?

like image 837
F16Falcon Avatar asked Dec 13 '22 09:12

F16Falcon


2 Answers

Use dict or orderdict(if the sort is important) group data by the date time .

from collections import defaultdict # use defaultdict like {}.setdefault(), it's very facility

mylist = [["Bob", "12-01 2:30"], ["Sal", "12-01 5:23"], ["Jill", "12-02 1:28"]]
record_dict = defaultdict(list)
# then iter the list group all date time.

for data in mylist:
    _, time = data
    date_time, _ = time.split(" ")
    record_dict[date_time].append(data)

res_list = list(record_dict.values())
print(res_list)

output:
[[['Bob', '12-01 2:30'], ['Sal', '12-01 5:23']], [['Jill', '12-02 1:28']]]

like image 171
DustyPosa Avatar answered Jan 26 '23 00:01

DustyPosa


A pure list-based solution as an alternative to the accepted dictionary-based solution. This offers the additional feature of easily sorting the whole list, first by date, then by hour, then by name

from itertools import groupby

mylist = [["Bob", "12-01 2:30"], ["Sal", "12-01 5:23"], ["Jill", "12-02 1:28"]]

newlist = [dt.split() + [name] for (name, dt) in mylist]
newlist.sort() # can be removed if inital data is already sorted by date
newlist = [list(group) for (date, group) in groupby(newlist, lambda item:item[0])]

# result:
# [[['12-01','2:30','Bob'], ['12-01','5:23','Sal']], [['12-02','1:28','Jill']]]

If you really want the same item format as the initial list, it requires a double iteration:

newlist = [[[name, date + ' ' + time] for (date, time, name) in group]
           for (date, group) in groupby(newlist, lambda item:item[0])]

# result:
# [[['Bob', '12-01 2:30'], ['Sal', '12-01 5:23']], [['Jill', '12-02 1:28']]]
like image 37
sciroccorics Avatar answered Jan 25 '23 23:01

sciroccorics