如何检查一个数字是否在一个列表的列表中?

3

我一直在尝试检查数字0是否在另一个列表内的一组列表中。这些行构成了我正在制作的类似吃豆人游戏的迷宫,因此这样做的目的是检查吃豆人是否已经吃掉了所有的硬币。

以下是我的代码:

row1 =[3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3]
row2 =[1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1]
row3 =[1,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,1]
row4 =[1,0,1,1,0,1,1,1,0,1,0,1,1,1,0,1,1,0,1]
row5 =[1,0,1,1,0,1,1,1,0,1,0,1,1,1,0,1,1,0,1]
row6 =[1,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,1]
row7 =[1,0,1,1,0,1,0,1,1,1,1,1,0,1,0,1,1,0,1]
row8 =[1,0,0,0,0,1,0,1,1,1,1,1,0,1,0,0,0,0,1]
row9 =[1,1,1,1,0,1,0,0,0,1,0,0,0,1,0,1,1,1,1]
row10=[3,3,3,1,0,1,1,1,0,1,0,1,1,1,0,1,3,3,3]
row11=[3,3,3,1,0,1,0,0,0,0,0,0,0,1,0,1,3,3,3]
row12=[3,3,3,1,0,1,0,1,4,4,4,1,0,1,0,1,3,3,3]
row13=[1,1,1,1,0,1,0,1,3,3,3,1,0,1,0,1,1,1,1]
row14=[3,3,3,3,0,0,0,1,3,3,3,1,0,0,0,3,3,3,3]
row15=[1,1,1,1,0,1,0,1,5,5,5,1,0,1,0,1,1,1,1]
row16=[3,3,3,1,0,1,0,3,3,3,3,3,0,1,0,1,3,3,3]
row17=[3,3,3,1,0,1,0,1,1,1,1,1,0,1,0,1,3,3,3]
row18=[3,3,3,1,0,1,0,1,1,1,1,1,0,1,0,1,3,3,3]
row19=[1,1,1,1,0,0,0,0,0,1,0,0,0,0,0,1,1,1,1]
row20=[1,0,0,0,0,1,1,1,0,1,0,1,1,1,0,0,0,0,1]
row21=[1,0,1,1,0,0,0,0,0,3,0,0,0,0,0,1,1,0,1]
row22=[1,0,1,1,0,1,0,1,1,1,1,1,0,1,0,1,1,0,1]
row23=[1,2,0,0,0,1,0,0,0,1,0,0,0,1,0,0,0,2,1]
row24=[1,0,1,1,1,1,1,1,0,1,0,1,1,1,1,1,1,0,1]
row25=[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1]
row26=[1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1]

maze = [row1,row2,row3,row4,row5,row6,row7,row8,row9,row10,row11,row12,
        row13,row14,row15,row16,row17,row18,row19,row20,row21,row22,
        row23,row24,row25,row26]

我尝试过if 0 not in maze:,但是无论(maze)中是否有0,if语句都会执行。

如果有帮助的话,感激不尽,谢谢。


not any(el == 0 for sublist in maze for el in sublist) - Christian Dean
@DYZ 对我来说很清楚。这个数字是 0 - Christian Dean
@leaf 标题说的是“数字”,而不是0。我不太清楚。 - DYZ
@DYZ但是如果您阅读第一句话,它字面上是说“0”。 - TerryA
好的,已经注意到了。 - That One Guy
显示剩余4条评论
5个回答

7
你需要遍历 maze 中的每个列表并检查是否存在 0:
if not any(0 in i for i in maze):
    ...

关于any()函数的优点是,它在找到0后停止遍历maze

1
你第一次尝试时,只在顶层列表中测试了0。当然,顶层列表只有列表,因此你的测试失败了。
你必须遍历maze中的每个子列表。你可以使用手动for循环,这是一个有效的选项:
def has_zero(maze):
    for sublist in maze:
        for el in sublist:
            if el == 0:
                return True
    return False

但是Python提供了更好的方法,使用any()函数(这基本上是上面函数的更好实现):

如果可迭代对象中有任何一个元素为真,则返回True。如果可迭代对象为空,则返回False[...]。

但是你还必须使用not运算符(在其他语言中称为!)来否定any()可能返回的True值。因此,完整的解决方案如下:

not any(el == 0 for sublist in maze for el in sublist)

1

any 已经被提到,但你也可以将列表展平(例如使用 itertools.chain.from_iterable),并检查是否包含该项:

from itertools import chain

if 0 in chain.from_iterable(lst):
    # do something

像任何一样,只要找到一个就会停止。仅提及此事是因为它经常被忽视:生成器和迭代器(如chain)通常支持in运算符。

0

循环遍历子列表。同时使用 any()

if any(0 in sublist for sublist in maze)

它将检查列表中是否有任何0


-1

只要我理解了你的问题,你可以使用以下代码:

a = [1,1,1]
b = [1,0,1]
c = [0,1,2]
d = [a,b,c]

for i in d:    
  if i.__contains__(0):
    print("yes") 

在你的代码中,几乎永远不应该使用__contains__或任何其他用双下划线括起来的东西。 - DYZ
谢谢你的建议,我在这里是新手,会去查看的。 - S_Ymln
你可以再详细解释一下这段代码的作用。 - JLT
@DYZ 你有任何支持你说法的来源吗?我一直以为不应该使用以单下划线开头的函数/属性/方法。 - MSeifert
@MSeifert https://dev59.com/Emoy5IYBdhLWcg3wPLn0 引用:“虽然可以直接调用这些方法(例如[10,20] .__ len __()),但下划线的存在表明这些方法是旨在间接调用的(例如len([10,20]))。” - DYZ
这不是官方文档!例如,PEP8(官方的)指出:“__double_leading_and_trailing_underscore__:存在于用户控制的命名空间中的“神奇”对象或属性。[...]。永远不要发明这样的名称;只能按照文档使用。”他们明确提到可以使用它们(如记录在文档中)。 - MSeifert

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接