如何在匹配模式后根据另一个列表中的预定义顺序对文件名列表进行排序?
How to sort filename list based on predefined order from another list after matching patterns?
我正在尝试对光栅列表进行排序 (rasters
)
rasters = '["example\\alt_canal.tif", "example\\back_garden.tif", "example\\main_entrance.tif", "example\\my_ditch.tif", "example\\ne_lawn.tif"]'
基于模式匹配和预定义顺序 (ras_order
)。
ras_order = '["ditch", "canal", "entrance", "garden", "lawn"]'
我遵循了这个 但它没有给我想要的东西。任何帮助表示赞赏。谢谢!
预期输出:
[u'example\my_ditch.tif', u'example\alt_canal.tif', u'example\main_entrance.tif', u'example\back_garden.tif', u'example\ne_lawn.tif']
示例代码:
import os
import arcpy
arcpy.CheckOutExtension("Spatial")
# set project directory
working_dir = os.path.expanduser('~/Documents/')
scenario = 'example'
env.workspace = os.path.join(working_dir, scenario)
# predefined order
ras_order = ['ditch', 'canal', 'entrance', 'garden', 'lawn']
# find rasters in the working_dir
rasters = []
walk = arcpy.da.Walk(os.path.join(working_dir, scenario), topdown=True, datatype="RasterDataset")
for dirpath, dirnames, filenames in walk:
for filename in filenames:
rasters.append(os.path.join(dirpath, filename))
print(rasters)
# [u'example\alt_canal.tif', u'example\back_garden.tif', u'example\main_entrance.tif', u'example\my_ditch.tif', u'example\ne_lawn.tif']
# sort based on predefined order (not working)
new_order1 = [x for _, x in sorted(zip(ras_order, rasters))]
print(new_order1)
# [u'example\back_garden.tif', u'example\alt_canal.tif', u'example\main_entrance.tif', u'example\my_ditch.tif', u'example\ne_lawn.tif']
除了@Lante 的回答之外,还有另一种方法:
new_raster = []
for i in ras_order:
for j in rasters:
if i in j:
new_raster.append(j)
new_raster
[u'example\\Max (dec).my_ditch.tif',
u'example\\Max (dec).alt_canal.tif',
u'example\\Max (dec).main_entrance.tif',
u'example\\Max (dec).back_garden.tif',
u'example\\Max (dec).ne_lawn.tif']
这是一个简单的解决方案,需要使用正则表达式进行优化以实现更精确的匹配:
rasters = ["example\\alt_canal.tif", "example\\back_garden.tif", "example\\main_entrance.tif", "example\\my_ditch.tif", "example\\ne_lawn.tif"]
ras_order = ["ditch", "canal", "entrance", "garden", "lawn"]
def ras_match(r, o):
return next(i for i, x in enumerate(o) if x in r)
sorted(rasters, key=lambda x: ras_match(x, ras_order))
输出:
['example\\my_ditch.tif',
'example\\alt_canal.tif',
'example\\main_entrance.tif',
'example\\back_garden.tif',
'example\\ne_lawn.tif']
我正在尝试对光栅列表进行排序 (rasters
)
rasters = '["example\\alt_canal.tif", "example\\back_garden.tif", "example\\main_entrance.tif", "example\\my_ditch.tif", "example\\ne_lawn.tif"]'
基于模式匹配和预定义顺序 (ras_order
)。
ras_order = '["ditch", "canal", "entrance", "garden", "lawn"]'
我遵循了这个
预期输出:
[u'example\my_ditch.tif', u'example\alt_canal.tif', u'example\main_entrance.tif', u'example\back_garden.tif', u'example\ne_lawn.tif']
示例代码:
import os
import arcpy
arcpy.CheckOutExtension("Spatial")
# set project directory
working_dir = os.path.expanduser('~/Documents/')
scenario = 'example'
env.workspace = os.path.join(working_dir, scenario)
# predefined order
ras_order = ['ditch', 'canal', 'entrance', 'garden', 'lawn']
# find rasters in the working_dir
rasters = []
walk = arcpy.da.Walk(os.path.join(working_dir, scenario), topdown=True, datatype="RasterDataset")
for dirpath, dirnames, filenames in walk:
for filename in filenames:
rasters.append(os.path.join(dirpath, filename))
print(rasters)
# [u'example\alt_canal.tif', u'example\back_garden.tif', u'example\main_entrance.tif', u'example\my_ditch.tif', u'example\ne_lawn.tif']
# sort based on predefined order (not working)
new_order1 = [x for _, x in sorted(zip(ras_order, rasters))]
print(new_order1)
# [u'example\back_garden.tif', u'example\alt_canal.tif', u'example\main_entrance.tif', u'example\my_ditch.tif', u'example\ne_lawn.tif']
除了@Lante 的回答之外,还有另一种方法:
new_raster = []
for i in ras_order:
for j in rasters:
if i in j:
new_raster.append(j)
new_raster
[u'example\\Max (dec).my_ditch.tif',
u'example\\Max (dec).alt_canal.tif',
u'example\\Max (dec).main_entrance.tif',
u'example\\Max (dec).back_garden.tif',
u'example\\Max (dec).ne_lawn.tif']
这是一个简单的解决方案,需要使用正则表达式进行优化以实现更精确的匹配:
rasters = ["example\\alt_canal.tif", "example\\back_garden.tif", "example\\main_entrance.tif", "example\\my_ditch.tif", "example\\ne_lawn.tif"]
ras_order = ["ditch", "canal", "entrance", "garden", "lawn"]
def ras_match(r, o):
return next(i for i, x in enumerate(o) if x in r)
sorted(rasters, key=lambda x: ras_match(x, ras_order))
输出:
['example\\my_ditch.tif',
'example\\alt_canal.tif',
'example\\main_entrance.tif',
'example\\back_garden.tif',
'example\\ne_lawn.tif']