The question is a bit vague on exactly what criteria is to be measured.
E.g. does it have to be an exact match , contain or start with.
Below is a comprehensive solution I made to come up with four cases and solutions.
There is also the additional element of matching anything in a tuple if the index is unknown.
If you find any issues with the code/have suggestions I'll happily edit.
There's also future proofing so using the list of items to be removed inline and not setting it to a variable should be avoided. This solution is therefore more general.
Using the below with:
final_device = remove_from_tuple_list(device,remove_list,0,match_type = 'contains')
Solves the OP's specific problem.
The code is fully commented with explantions.
device = [('nvme2n1',),
('nvme1n1', '/local'),
('nvme0n1',),
('nvme0n1p1', '/'),
('nvme0n1p128',),
('nvme3n1',)]
remove_list = ['nvme1n1', 'nvme0n1p1' , 'nvme0n1p128', 'nvme0n1']
def analyze_item_criteria(item : str ,criteria : list,criteria_type : str):
'''
Check whether an item string or tuple is contained in a list of items
Args:
item : the item to be evaluated
criteria : list of items to be checked against
criteria_type: the type of criteria
Returns:
Boolean True/False if evaluated
None if not evaluated
Raises:
'Invalid criteria_type specified' : if the item is not a valid criteria type
'''
##Check that type is valid
assert criteria_type in ['contains',
'exact',
'starts_with',
'ends_with',
],'Invalid criteria_type specified'
if criteria_type == 'exact':
if item in criteria:
return True
else:
return False
##Starts with/ends with also takes a tupe (.startswith((args,))) this implementation
##Isn't really different from what happens under the hood
elif criteria_type == 'starts_with':
if any([item.startswith(x) for x in criteria] ):
return True
else:
return False
elif criteria_type == 'ends_with':
if any([item.endswith(x) for x in criteria] ):
return True
else:
return False
elif criteria_type == 'contains':
if any([x in item for x in criteria]):
return True
else:
return False
#Specifying no index does not really work with well exact but the other three options are still valid
def remove_from_tuple_list(tuple_list : list, remove_list :list, tuple_index : int = None, match_type : str = 'contains'):
'''
Function to remove items from a list of tuples containing specific words.
The function can remove items at a specified index or any position if not specified
Args:
tuple_list : The list of tuples from which items are to be removed (items in tuple have to be str/int/float , objects will
have unexpected behaviour)
remove_list : list of strings/items to be removed from the tuple_list
tuple_index : if an integer, checks for criteria at the specific position otherwise the whole tuple which is inefficient
Set to none if you want to analyze a list of strings for example as well
match_type : Do we want to match the word exactly or do we look for it containing the word
There are a few cases to consider here.
- contains
- exact
- starts_with
- ends_with
Returns:
list of items not in remove_list
Raises:
'Invalid match_type specified' : if the item is not in the match list
'''
##Check that type is valid
assert match_type in ['contains',
'exact',
'starts_with',
'ends_with',
],'Invalid match_type specified'
new_tuple_list = []
#Check whether we are looking at a specific index in the tuple
##This can be done multiple ways, think analysing the if once is the most efficient so justifies the additional typing
if isinstance(tuple_index,int):
new_tuple_list = [
list_item for list_item in tuple_list
if not analyze_item_criteria(list_item[tuple_index],remove_list,match_type)
]
else:
new_tuple_list = [list_item for list_item in tuple_list if not analyze_item_criteria('|'.join([str(x) for x in list_item])
,remove_list,match_type)]
return new_tuple_list
def test():
final_device = remove_from_tuple_list(device,remove_list,0,match_type = 'contains')
print(remove_from_tuple_list(device,remove_list,0,match_type = 'contains'))
print(remove_from_tuple_list(device,remove_list,0,match_type = 'exact'))
remove_list = ['nvme1n1', 'nvme0n1p1', 'nvme0n1']
print(remove_from_tuple_list(device,remove_list,0,match_type = 'ends_with'))
print(remove_from_tuple_list(device,remove_list,0,match_type = 'starts_with'))
print(remove_from_tuple_list(device,remove_list,None,match_type = 'contains'))
print(remove_from_tuple_list(device,remove_list,None,match_type = 'exact'))
remove_list = ['nvme1n1', 'nvme0n1p1', 'nvme0n1']
print(remove_from_tuple_list(device,remove_list,None,match_type = 'ends_with'))
print(remove_from_tuple_list(device,remove_list,None,match_type = 'starts_with'))
'''
Output:
-------
[('nvme2n1',), ('nvme3n1',)]
[('nvme2n1',), ('nvme3n1',)]
[('nvme2n1',), ('nvme0n1p128',), ('nvme3n1',)]
[('nvme2n1',), ('nvme3n1',)]
[('nvme2n1',), ('nvme3n1',)]
[('nvme2n1',), ('nvme1n1', '/local'), ('nvme0n1p1', '/'), ('nvme0n1p128',), ('nvme3n1',)]
[('nvme2n1',), ('nvme1n1', '/local'), ('nvme0n1p1', '/'), ('nvme0n1p128',), ('nvme3n1',)]
[('nvme2n1',), ('nvme3n1',)]
'''