如果元组的第一项等于任何给定的字符串,则从列表中删除元组

dbN*_*ice 7 python

我有一个列表如下:

device = [('nvme2n1',), 
          ('nvme1n1', '/local'), 
          ('nvme0n1',), 
          ('nvme0n1p1', '/'),
          ('nvme0n1p128',), 
          ('nvme3n1',)]
Run Code Online (Sandbox Code Playgroud)

我想从这个列表中删除几个包含nvme1n1ornvme0n1p1nvme0n1p128or 的元组nvme0n1

所以最终名单将有

final_device = [('nvme2n1',),('nvme3n1',)]
Run Code Online (Sandbox Code Playgroud)

尝试如下但没有工作并出现错误 "AttributeError: 'tuple' object has no attribute 'startswith'"

for word in devices[:]: 
    if word.startswith("nvme0n1","nvme0n1p1","nvme0n1p128"): 
        devices.remove(word)
Run Code Online (Sandbox Code Playgroud)

有人能帮忙吗?

bur*_*ran 7

devices = [('nvme2n1',), ('nvme1n1', '/local'),
           ('nvme0n1',), ('nvme0n1p1', '/'), 
           ('nvme0n1p128',), ('nvme3n1',)]
devices = [device for device in devices if device[0] not in 
           (("nvme0n1", "nvme0n1p1", "nvme0n1p128", "nvme0n1"))]
print(devices)
Run Code Online (Sandbox Code Playgroud)

输出

[('nvme2n1',), ('nvme1n1', '/local'), ('nvme3n1',)]
Run Code Online (Sandbox Code Playgroud)

@JamesTollefson 在他们的回答中解决了代码中的特定问题以及如何解决它。这只是不同的,在我看来更好/更清洁的方式来实现你想要的。


Jam*_*son 5

word您在devices列表中迭代的s是元组。您需要访问您感兴趣的元组的那部分,如下所示:

for word in devices[:]: 
    if word[0] in ["nvme0n1","nvme0n1p1","nvme0n1p128"]: 
        devices.remove(word)
Run Code Online (Sandbox Code Playgroud)

  • @Asker @JamesTollefson `[:]` 实际上是它工作所必需的,否则你在迭代列表时修改列表,这将导致某些元素被跳过。尝试使用 `devices = [(1,), (2,), (3,), (4,)]` 和 `if word[0] in [1, 2, 3]: ...` -结果列表是“[(2,),(4,)]”,即“(2,)”不会被删除。这种行为在[此处](/sf/ask/438206261/)和[此处]( /sf/ask/84518451/)。 (3认同)

Dur*_*oop 5

您甚至可以使用列表理解来简化它。正如詹姆斯在他的回答中提到的,你需要word[0]按照word元组而不是字符串来做。

startswith 可以带一个元组来检查。

[dev for dev in devices if not dev[0].startswith(("nvme0n1","nvme0n1p1","nvme0n1p128"))]
Run Code Online (Sandbox Code Playgroud)

但如果你正在寻找精确匹配,你可以这样做,

[dev for dev in devices if dev[0] not in ("nvme0n1","nvme0n1p1","nvme0n1p128")]
Run Code Online (Sandbox Code Playgroud)