I want to group items in a list with a specific order. The order I want is in groups
and the items
must be grouped by that order.
The solution I've tried is to pop the item[index] in items when I append it to temp, but it's not a good idea to manipulate a list while iterating it.
Is there a better approach or any other way to optimize this sample code?
groups = ["d", "c", "a", "b"]
items = ["a", "b", "b", "c", "d", "a"]
result = []
for group in groups:
temp = []
for item in items:
if item == group:
temp.append(item)
result.extend(temp)
print(result)
CodePudding user response:
You could get the frequency of all the items, then flatten in order of groups... eg:
from collections import Counter
counts = Counter(items)
result = [k for k in groups for n in range(counts[k])]
# ['d', 'c', 'a', 'a', 'b', 'b']
CodePudding user response:
It looks like you're sorting more than grouping. There are a couple of ways to approach this.
One way would be a sort with a key based on groups
. To avoid the O(n)
lookup every time you call groups.index
, convert it to dict
and use get
or __getitem__
instead:
groupdict = {g: i for i, g in enumerate(groups)}
result = sorted(items, key=groupdict.__getitem__)
CodePudding user response:
You don't really need to sort the list; you can just count how many instances of an item there are, then add that many instances to your result list. Iterate through your groups
list. You begin with "d"
. There is one instance of "d"
in items
. Therefore, you append "d"
to result
one time.
groups = ["d", "c", "a", "b"]
items = ["a", "b", "b", "c", "d", "a"]
result = []
for group in groups:
for i in range(items.count(group)):
result.append(group)
print(result)
# ['d', 'c', 'a', 'a', 'b', 'b']