Cómo propagar nodos de árbol en Python

I am dealing with a tree structure in a Python program. Each node in a tree has a dictionary "sons", whose keys hold arc information, and values are the son nodes. The question is to propagate a list of nodes to all their sons. I use:

current_nodes = reduce(lambda s,x:s+x, map(lambda node:node.sons.values(),current_nodes),[])

Dónde current_nodes is the initial (and updated) list of nodes.

My program spends most time executing this reduce operation. Is there a faster way to implement that?


EDIT: Hi, Just let you know that the code: sum((node.sons.values() for node in current_nodes), []) although pythonic, is not really significantly faster -- if the list of nodes is long (>20000), the propagation slows down unproportionally, actually, very slow. I don't know why.

Then I define:

def Ext(nodes)
    for node in nodes:
    return l

Entonces uso: current_node = Ext(current_node). This approach is actually much faster. I guess sum() function is not as efficient as a list's extend method when handling list concatenation.

preguntado el 28 de agosto de 11 a las 03:08

why you're using that ugly reduce cuando sum does the job? Same thing to that ugly map: List comprehensions FTW -

Can sum concatenate a list of lists? -

I got it. sum([node.sons.values() for node in current_nodes],[]) -

sip, sum needs a base element to serve as the "accumulator" (in case the sequence is empty, and so that the first element of a non-empty sequence doesn't need special handling), which defaults to 0, but can be replaced. To sum lists, you just start with an empty list. However, sum will arbitrarily refuse to sum(['foo', 'bar', 'baz'], ''), and tell you to use the ''.join idiom instead. Personally I think this was a rather overzealous application of TSBOWTDI :( -

BTW, "children" is the canonical name for such a data member... -

1 Respuestas

from itertools import chain
list(chain.from_iterable(node.sons.values() for node in current_nodes))

Should be faster. map y reduce on lambdas are slow. I don't know how fast chain is; you could try

sum((node.sons.values() for node in current_nodes), [])


Respondido 28 ago 11, 07:08

I thought you were taking a break ;) - Neil G

I'm logging in once a day to work on my flag weight and I happened to see this :) - agf

No es la respuesta que estás buscando? Examinar otras preguntas etiquetadas or haz tu propia pregunta.