user2242044
user2242044

Reputation: 9233

return items from one list if not in the other

I want to return the items from Project if that project does not appear in my task list, Task. My code only returns everything and in Project. What am I doing wrong?

Task = [['Task1','Project1',3],['Task2','Project4',6]]
Project = [['Project1', 'Andrew'],['Project2','Bob'],['Project3','Bob']]

not_in_list = [item for item in Project if item[0] not in Case]

print not_in_list

Output:

[['Project1', 'Andrew'], ['Project2', 'Bob'], ['Project3', 'Bob']]

Expected Result:

[['Project2', 'Bob'],['Project3', 'Bob']]

Upvotes: 0

Views: 74

Answers (3)

glglgl
glglgl

Reputation: 91109

task = [['Task1','Project1',3],['Task2','Project4',6]]
project = [['Project1', 'Andrew'],['Project2','Bob'],['Project3','Bob']]
task_projects = set(pr for _, pr, _ in task)

not_in_list = [item for item in project if item[0] not in task_projects]

print not_in_list

(Note that I changed the variable names so that they match the recommendations.)

This code first creates a set of project names present. Checking for existence of an item in a set is much cheaper than in a list.

Upvotes: 0

dylrei
dylrei

Reputation: 1736

Only slightly more efficient than the previous answer, if you can assume Project name is always in index 1 of Task:

>>> Task = [['Task1','Project1',3],['Task2','Project4',6]]
>>> Project = [['Project1', 'Andrew'],['Project2','Bob'],['Project3','Bob']]
>>> assigned = [t[1] for t in Task]
>>> [p for p in Project if p[0] not in assigned]
[['Project2', 'Bob'], ['Project3', 'Bob']]

Upvotes: 0

georg
georg

Reputation: 215009

This does the trick:

Task = [['Task1','Project1',3],['Task2','Project4',6]]
Project = [['Project1', 'Andrew'],['Project2','Bob'],['Project3','Bob']]

no_tasks = [p for p in Project if all(p[0] not in t for t in Task)]
print no_tasks

but will be horribly inefficient for large lists. Time to reconsider your data structure!

Upvotes: 2

Related Questions