Python 打印列表中每行已更改列的索引
下面的循环通过两个列表(源和主列表)扫描匹配的ID(索引0),然后对于ID匹配的行,它会查找已更改的列并打印它们:Python 打印列表中每行已更改列的索引,python,list,Python,List,下面的循环通过两个列表(源和主列表)扫描匹配的ID(索引0),然后对于ID匹配的行,它会查找已更改的列并打印它们: for row in source: identifier = row[0] new_cols = row[1:] for row in master: old_cols = row[1:] if identifier == row
for row in source:
identifier = row[0]
new_cols = row[1:]
for row in master:
old_cols = row[1:]
if identifier == row[0]:
print(row[0]) # ID that matched
changed_cols = [col for col in new_cols if col not in old_cols]
print(changed_cols) # cols that differ
列表每行包含20多列,因此我认为使用行[1:]会很明智,但我不确定如何使用此方法获取更改的列的索引。谢谢你的帮助
更新:
source = [['1002', '', '', '', '13RA11', '', 'LO', '4302', '99111', '0', ''],
['1076', '', '', '', '13RA11', '', 'LO', '4302', '999111', '0', ''],
['1130', '', '', '', '11HOT1A', '', 'LO', '4302', '99111', '0', '']]
master = [['1002', '', '', '', '13RA11', '', 'LO', '4302', '99111', '0', ''],
['1076', '', '', '', '13RA11', '', 'LO', '4302', '999111', '1', ''],
['1130', '', '', '', '13RA11', '', 'LO', '4302', '99111', '1', '']]
尝试创建一个过滤器,并使用
zip
将每个匹配行折叠在一起(即,将源代码和主代码中具有匹配ID的行压缩在一起。)
对于source_row1=[1,6,3,8],master_row1=[5,6,7,8]
这将打印索引1和索引3。如果你愿意,你也可以把整个事情放在一个列表中,如下所示:
changed_cols = [enum for enum, item in enumerate(bool_gen(zip(source_row1, master_row1))) if (item == True)]
# changed_cols returns [1, 3]
将此建议用于您的代码:
for row in source:
identifier = row[0]
new_cols = row[1:]
for row in master:
old_cols = row[1:]
if identifier == row[0]:
print(row[0]) # ID that matched
changed_cols = [enum for enum, item in enumerate(bool_gen(zip(new_cols, old_cols))) if (item == True)]
print(changed_cols) # cols that differ
但是,正如您所看到的,它既不能减少所需的代码量,也不能提高可读性。我不确定哪种代码更有效
如果我们的答案不正确,请告诉我们。如果是,请在问题中添加更多详细信息。您是否考虑过使用
枚举?您的列表理解将更改为:
changed_cols = [(ID,col) for ID,col in enumerate(new_cols) if col not in old_cols]
对我来说,这似乎是最简单的解决办法
如果我误解了您的问题,请告诉我,我将努力调整我的解决方案:)
编辑:我想你可能想要加里建议的东西:
changed_cols = [(ID,col) for ID,col in enumerate(new_cols) if col != old_cols[ID]]
这将仅比较每个新列对应的旧列。我猜这就是你真正想要的功能。如果您不确定差异,请告诉我:)您应该保留列号以进行比较。如果不这样做,则不会检测到两列之间的交换。你可以做:
for row in source:
identifier = row[0]
new_cols = row[1:]
for row in master:
if identifier == row[0]:
old_cols = row[1:]
print(row[0]) # ID that matched
n = len(new_cols) if len(new_cols) <= len(old_cols) else len(old_cols)
changed_cols = [(i, old_cols[i], new_col[i]) for i in range(n) if new_cols[i] != old_cols[i ]]
print(changed_cols) # cols that differ
if len(new_cols) < len(old_cols): print(len(old_cols)-len(new_cols), " cols missing")
if len(new_cols) > len(old_cols): print(len(new_cols)-len(old_cols), " cols added")
对于源中的行:
标识符=行[0]
新列=行[1:]
对于主控中的行:
如果标识符==行[0]:
old_cols=行[1:]
打印(第[0]行)#匹配的ID
n=len(新列)如果len(新列)len(旧列):打印(len(新列)-len(旧列),“添加列”)
我对您想要实现的目标有点困惑。给定源行[1,0,0,0]
和相应的主行[1,0,0,1]
,您的代码(以及我的答案中的代码)将不会拾取任何“已更改的列”。你确定这就是你想要的吗?或者你想要加里贴的东西?嗯。。。您可能必须小心该行中的重复条目。请记住,如果col
在列表中的任何位置old\u cols
,则条件col not in old\u cols
将为false。这是你想要的吗?我将为我的解决方案添加一个可能是您实际需要的替代方案。此代码的功能与OP使用的列表不同。虽然这似乎更有意义。谢谢!您的解决方案使我对整个过程有了更好的了解(很高兴我们能提供帮助:)
for row in source:
identifier = row[0]
new_cols = row[1:]
for row in master:
if identifier == row[0]:
old_cols = row[1:]
print(row[0]) # ID that matched
n = len(new_cols) if len(new_cols) <= len(old_cols) else len(old_cols)
changed_cols = [(i, old_cols[i], new_col[i]) for i in range(n) if new_cols[i] != old_cols[i ]]
print(changed_cols) # cols that differ
if len(new_cols) < len(old_cols): print(len(old_cols)-len(new_cols), " cols missing")
if len(new_cols) > len(old_cols): print(len(new_cols)-len(old_cols), " cols added")