Python:如果满足条件,用另一个列表的元素替换一个列表的元素
Python: Replace elements of one list with those of another if condition is met
我有两个列表,一个叫做 src,每个元素都采用这种格式:
['SOURCE: filename.dc : 1 : a/path/: description','...]
还有一个名为 base 的元素采用这种格式:
['BASE: 1: another/path','...]
我正在尝试比较基本元素的编号(在本例中为 4)与源元素的编号(在本例中为 1)。
如果它们匹配,那么我想用基本元素的路径替换源元素的编号。
现在我可以像这样用 for 循环拆分源元素的编号:
for w in source_list:
src_no=(map(lambda s: s.strip(), w.split(':'))[2])
我可以像这样用 for 循环拆分基本元素的路径和编号:
for r in basepaths:
base_no=(map(lambda s: s.strip(), r.split(':'))[1])
base_path=(map(lambda s: s.strip(), r.split(':'))[2])
我希望新列表看起来像(基于上面两个元素的示例):
['SOURCE: filename.dc : another/path : a/path/: description','...]
src列表是一个包含很多元素的大列表,基本列表通常有三四个元素长,只用于转换成新列表。
所以有一个较大的列表将被顺序浏览和一个较短的列表。我会把短的变成一个映射,以立即为第一个列表的每个项目查找是否有匹配项:
base = {}
for r in basepaths:
base_no=(map(lambda s: s.strip(), r.split(':'))[1])
base_path=(map(lambda s: s.strip(), r.split(':'))[2])
base[base_no] = base_path
for w in enumerate source_list:
src_no=(map(lambda s: s.strip(), w.split(':'))[2])
if src_no in base:
path = base[src_no]
# stuff...
像这样:
for i in range(len(source_list)):
for b in basepaths:
if source_list[i].split(":")[2].strip() == b.split(":")[1].strip():
source_list[i] = ":".join(source_list[i].split(":")[:3] + [b.split(":")[2]] + source_list[i].split(":")[4:])
只去掉拆分的[]部分:
src=(map(lambda s: s.strip(), w.split(':')))
base=(map(lambda s: s.strip(), r.split(':')))
>> src
>> ['SOURCE', 'filename.dc', '1', 'a/path/', 'description']
基础同样是一个简单的列表
现在只需替换正确的元素:
src[2] = base[2]
然后根据需要将元素放回原处:
src = ' : '.join(src)
def separate(x, separator = ':'):
return tuple(x.split(separator))
sourceList = map(separate, source)
baseDict = {}
for b in map(separate, base):
baseDict[int(b[1])] = b[2]
def tryFind(number):
try:
return baseDict[number]
except:
return number
result = [(s[0], s[1], tryFind(int(s[2])), s[3]) for s in sourceList]
这对我有用,它不是最好的,但是一个开始
我为你整理了一些东西,我认为应该可以满足你的要求:
base_list = ['BASE: 1: another/path']
base_dict = dict()
# First map the base numbers to the paths
for entry in base_list:
n, p = map(lambda s: s.strip(), entry.split(':')[1:])
base_dict[n] = p
source_list = ['SOURCE: filename.dc : 1 : a/path/: description']
# Loop over all source entries and replace the number with the base path of the numbers match
for i, entry in enumerate(source_list):
n = entry.split(':')[2].strip()
if n in base_dict:
new_entry = entry.split(':')
new_entry[2] = base_dict[n]
source_list[i] = ':'.join(new_entry)
请注意,这是一个 hacky 解决方案,我认为您应该使用正则表达式(查看 re 模块)来提取数字和路径,并在替换数字时使用。
此代码还会在遍历列表时更改列表,这可能不是最符合 Python 风格的事情。
我有两个列表,一个叫做 src,每个元素都采用这种格式:
['SOURCE: filename.dc : 1 : a/path/: description','...]
还有一个名为 base 的元素采用这种格式:
['BASE: 1: another/path','...]
我正在尝试比较基本元素的编号(在本例中为 4)与源元素的编号(在本例中为 1)。
如果它们匹配,那么我想用基本元素的路径替换源元素的编号。
现在我可以像这样用 for 循环拆分源元素的编号:
for w in source_list:
src_no=(map(lambda s: s.strip(), w.split(':'))[2])
我可以像这样用 for 循环拆分基本元素的路径和编号:
for r in basepaths:
base_no=(map(lambda s: s.strip(), r.split(':'))[1])
base_path=(map(lambda s: s.strip(), r.split(':'))[2])
我希望新列表看起来像(基于上面两个元素的示例):
['SOURCE: filename.dc : another/path : a/path/: description','...]
src列表是一个包含很多元素的大列表,基本列表通常有三四个元素长,只用于转换成新列表。
所以有一个较大的列表将被顺序浏览和一个较短的列表。我会把短的变成一个映射,以立即为第一个列表的每个项目查找是否有匹配项:
base = {}
for r in basepaths:
base_no=(map(lambda s: s.strip(), r.split(':'))[1])
base_path=(map(lambda s: s.strip(), r.split(':'))[2])
base[base_no] = base_path
for w in enumerate source_list:
src_no=(map(lambda s: s.strip(), w.split(':'))[2])
if src_no in base:
path = base[src_no]
# stuff...
像这样:
for i in range(len(source_list)):
for b in basepaths:
if source_list[i].split(":")[2].strip() == b.split(":")[1].strip():
source_list[i] = ":".join(source_list[i].split(":")[:3] + [b.split(":")[2]] + source_list[i].split(":")[4:])
只去掉拆分的[]部分:
src=(map(lambda s: s.strip(), w.split(':')))
base=(map(lambda s: s.strip(), r.split(':')))
>> src
>> ['SOURCE', 'filename.dc', '1', 'a/path/', 'description']
基础同样是一个简单的列表 现在只需替换正确的元素:
src[2] = base[2]
然后根据需要将元素放回原处:
src = ' : '.join(src)
def separate(x, separator = ':'):
return tuple(x.split(separator))
sourceList = map(separate, source)
baseDict = {}
for b in map(separate, base):
baseDict[int(b[1])] = b[2]
def tryFind(number):
try:
return baseDict[number]
except:
return number
result = [(s[0], s[1], tryFind(int(s[2])), s[3]) for s in sourceList]
这对我有用,它不是最好的,但是一个开始
我为你整理了一些东西,我认为应该可以满足你的要求:
base_list = ['BASE: 1: another/path']
base_dict = dict()
# First map the base numbers to the paths
for entry in base_list:
n, p = map(lambda s: s.strip(), entry.split(':')[1:])
base_dict[n] = p
source_list = ['SOURCE: filename.dc : 1 : a/path/: description']
# Loop over all source entries and replace the number with the base path of the numbers match
for i, entry in enumerate(source_list):
n = entry.split(':')[2].strip()
if n in base_dict:
new_entry = entry.split(':')
new_entry[2] = base_dict[n]
source_list[i] = ':'.join(new_entry)
请注意,这是一个 hacky 解决方案,我认为您应该使用正则表达式(查看 re 模块)来提取数字和路径,并在替换数字时使用。
此代码还会在遍历列表时更改列表,这可能不是最符合 Python 风格的事情。