簡體   English   中英

如果值出現在元組列表中,則條件為真

[英]while condition true if value appears in list of tuples

我是 Python 的新手,在實現繪制圖形的算法時被卡住了。 我有一個包含某些節點及其“級別”(用於分層)的元組列表。 最初看起來像這樣:

[(0, 10), (1, 'empty'), (2, 'empty'), (3, 'empty'), (4, 'empty'), (5, 'empty'), (6, 'empty'), (7, 'empty'), (8, 'empty'), (9, 'empty')] (node,level)

現在我需要為這些節點分配級別,只要任何節點沒有級別,相應的“空”屬性。

我嘗試了幾種可能的 while 條件結構,在語法上沒有錯,但在語義上沒有任何意義,因為 while 循環沒有終止:

while (True for node, level in g.nodes(data='level') if level == 'empty'):

或者

while ( 'empty' in enumerate(g.nodes(data='level') ):

以及某些其他類似的構造,它們不起作用,我不記得了..

直到現在,我似乎還不清楚為什么這不起作用 - python 甚至沒有在這些條件下進入 while 循環。 你能解釋一下原因並告訴我如何解決它嗎?

提示: g.nodes(data='level') 是一個 networkx function,它返回元組的上層列表

因此,括號中的內容是生成器表達式,它們總是評估為True

你有正確的想法,但可能需要更多地了解這些表達式以及如何處理它們。 在您的第一個建議中,我_認為_您的意思是:

while any(level == 'empty' for node, level in g.nodes(data='level')):
  ...

在您的版本中,您所做的是創建一個生成器表達式,該表達式將包含多個True值,每個級別一個為empty 但是,即使該生成器表達式中沒有元素,它本身也不是一個空的 object,因此它的計算結果為True

你可以試試這個:

bool([]) # --> False because empty sequence
bool(list(range(1, -10))) # --> False because empty sequence
bool((i for i in range(1,-10))) # --> True because non-None generator expression

所以你需要把你的生成器表達式變成一個真值,它實際上反映了它是否有任何真正的元素,這就是any function 所做的:取一個迭代器(或一個生成器表達式)並返回 true 如果它的任何元素是真的。

你正試圖通過元素檢查來尋找你。 相反,專注於准確提取您需要檢查的值。 讓我們從元組列表開始

g = [(0, 10), (1, 'empty'), (2, 'empty'), (3, 'empty'), (4, 'empty'),
     (5, 'empty'), (6, 'empty'), (7, 'empty'), (8, 'empty'), (9, 'empty')]

現在獲取僅包含級別的列表:

level = [node[1] for node in g]

現在,你的支票很簡單

while "empty" in level:
    # Assign levels as appropriate
    # Repeat the check for "empty"
    level = [node[1] for node in g]

如果您一直在更新主圖g ,則將級別提取折疊到while

while "empty" in [node[1] for node in g]:
    # Assign levels

最初,您的while失敗了,因為只要g中有任何內容,您就會返回True

while (True for node, level in ...)

你有一個很好的方法,但是讓它太復雜了一層,並且被True卡住了。

您的enumerate嘗試失敗,因為您在枚舉器中搜索字符串,而不是在其返回值中。 您可以制作一個返回值的列表,但是我們又回到了我們開始的地方,帶有一個元組列表。 這會將“空”與每個元組進行比較,並且無法找到所需的字符串——它比下一層更遠。

其他答案可能是最好的。 但是您要求的具體測試可以寫成幾種方式:

這與您所擁有的類似,但創建了一個列表而不是生成器。 如果列表為空,則列表將評估為False ,但生成器不會。

while [True for node, level in g.nodes(data='level') if level == 'empty']:
   ...

這是一個同樣有效的版本。 該列表必須為空或不為空; 元素是True還是False或其他東西都沒有關系:

while [node for node, level in g.nodes(data='level') if level == 'empty']:
   ...

或者您可以使用 Python 的any function,它是為此而設計的,並且效率更高(它在第一次匹配后停止檢查元素)。 這可以使用生成器或列表。

while any(level == 'empty' for node, level in g.nodes(data='level')):
   ...

如果您只是想為每個級別分配級別,如果一個為空,那么一個簡單的 for 循環就足夠了:

data = [(0, 10), (1, 'empty'), (2, 'empty'), (3, 'empty'), (4, 'empty'), (5, 'empty'), (6, 'empty'), (7, 'empty'), (8, 'empty'), (9, 'empty')]
output = []

for node, level in data:
    if level == 'empty':
        level = ? #question mark is whatever level logic you wish to insert
    output.append((node, level))

使用 for 循環通常更符合 Pythonic:

nodes = [(0, 10),
         (1, 'empty'),
         (2, 'empty'),
         (3, 'empty'),
         (4, 'empty'),
         (5, 'empty'),
         (6, 'empty'),
         (7, 'empty'),
         (8, 'empty'),
         (9, 'empty')]

for node in nodes:
    if node[1]=="empty":
        node[1] = set_level_func() # customise this function as you wish
    

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM