根据多个条件过滤列表

时间:2018-12-15 17:33:24

标签: python

我正在根据下面的列表学习Python,我想根据几种不同的条件进行过滤并组合结果。

list_of_stuff = [
    "aus-airport-1",
    "aus-airport-2",
    "us-airport-1",
    "us-airport-2",
    "aus-ship-1",
    "us-ship-99",
    "nz-airport-1"
]

该程序应能够允许用户:

  • 打印除nz以外的所有区域
  • 打印澳大利亚的所有地区
  • 打印所有船只

下面是我的想法的一个模拟,我确信必须有一个更好的模式,例如map,filter,reduce甚至是内置的filter,因此需要寻求改进方法的帮助。该程序将接受用户输入,并且仅在指定了过滤器类型的情况下进行过滤。例如list_of_stuff --exclude_region nz --transport ship。

我的模拟尝试

def filter_transport(stuff,transport):
    if transport:
        if stuff.split("-")[1] == transport:
            return True
        else:
            return False
    else:
        return True    

def exclude_region(stuff,region):
    if region:
        if stuff.split("-")[0] ==region:
            return True
    else:
        return False    

def included_region(stuff,region):
    if region:
        if stuff.split("-")[0] ==region:
            return True
        else:
            return False
    else:
        return True    

def filters(stuff,transport=None,include_region=None,excluded_region=None):
    if( filter_transport(stuff,transport) and 
        included_region(stuff,include_region) and not exclude_region(stuff,excluded_region)  ):
        return True    


#give all airports excluding nz
stuff = [stuff for stuff in list_of_stuff if filters(stuff,transport="airport",excluded_region="nz")]
print (stuff)
#give all airports in aus
stuff = [stuff for stuff in list_of_stuff if filters(stuff,transport="airport",include_region="aus")]
print (stuff)
#give all ships
stuff = [stuff for stuff in list_of_stuff if filters(stuff,transport="ship")]
print (stuff)

4 个答案:

答案 0 :(得分:0)

您可以使用三种直接的列表理解:

lst = ["aus-airport-1","aus-airport-2","us-airport-1","us-airport-2","aus-ship-1","us-ship-99","nz-airport-1"]

splits = list(map(lambda x: x.split('-'), lst))

lst1 = [x for x in splits if x[1] == 'airport' and x[0] != 'nz']
print(f'All airports excluding nz: {lst1}')

lst2 = [x for x in splits if x[1] == 'airport' and x[0] == 'aus']
print(f'All airports in aus: {lst2}')

lst3 = [x for x in splits if x[1] == 'ship']
print(f'All ships: {lst3}')

答案 1 :(得分:0)

这样吧:

import argparse 

parser = argparse.ArgumentParser()
parser.add_argument("--exclude-region", dest="excluded_region", action="store")
parser.add_argument("--only-region", dest="only_region", action="store")
parser.add_argument("--transport", dest="transport", action="store")
args_space = parser.parse_args()


list_of_stuff = [
    "aus-airport-1",
    "aus-airport-2",
    "us-airport-1",
    "us-airport-2",
    "aus-ship-1",
    "us-ship-99",
    "nz-airport-1"
]


def exclude_by_country(country, elements):
    return filter(lambda x: x.split('-')[0] != country, elements)

def filter_by_country(country, elements):
    return filter(lambda x: x.split('-')[0] == country, elements)

def filter_by_type(vehicle_type, elements):
    return filter(lambda x: x.split('-')[1] == vehicle_type, elements)


results = list_of_stuff

if args_space.excluded_region:
    results = exclude_by_country(args_space.excluded_region, results)

if args_space.only_region:
    results = filter_by_country(args_space.only_region, results)

if args_space.transport:
    results = filter_by_type(args_space.transport, results)

print([x for x in results])

答案 2 :(得分:0)

您可以filter列表:

http://localhost:8081/api

Check results

list_of_stuff = [
    "aus-airport-1",
    "aus-airport-2",
    "us-airport-1",
    "us-airport-2",
    "aus-ship-1",
    "us-ship-99",
    "nz-airport-1"
]

is_airport = lambda x: "-airport-" in x
is_ship = lambda x: "-ship-" in x

airports_excluding_nz = lambda x: is_airport(x) and not x.startswith("nz-")
airports_in_aus = lambda x: is_airport(x) and x.startswith("nz-")
ships = lambda x: is_ship(x)

print ("all regions excluding nz:" , 
       ", ".join( filter(lambda x: airports_excluding_nz(x) , list_of_stuff) ) )
print ("all regions in aus:", 
       ", ".join( filter(lambda x: airports_in_aus(x) , list_of_stuff) ) )
print ("all ships:", 
       ", ".join( filter(lambda x: ships(x) , list_of_stuff) ) )

答案 3 :(得分:0)

我们也可以使用正则表达式对其进行过滤,如下所示:

条件

不包含region并且包含transport

res = [k for k in list_of_stuff if bool(re.search('(?=.*-' + transport + '-.*)(^((?!' + region + '-).)*$)', k))]

完整的示例代码是

import re
list_of_stuff = ["aus-airport-1",
    "aus-airport-2",
    "us-airport-1",
    "us-airport-2",
    "aus-ship-1",
    "us-ship-99",
    "nz-airport-1"]

region = 'aus'
transport = 'ship'
res = [k for k in list_of_stuff if bool(re.search('(?=.*-' + transport + '-.*)(^((?!' + region + '-).)*$)', k))]
print(res)

输出是

['us-ship-99']