Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'intern/python/modules/mcf/utils/hier_rx.py')
-rw-r--r--intern/python/modules/mcf/utils/hier_rx.py201
1 files changed, 201 insertions, 0 deletions
diff --git a/intern/python/modules/mcf/utils/hier_rx.py b/intern/python/modules/mcf/utils/hier_rx.py
new file mode 100644
index 00000000000..3770f0bab22
--- /dev/null
+++ b/intern/python/modules/mcf/utils/hier_rx.py
@@ -0,0 +1,201 @@
+'''
+Simple Hierarchic Walking functions for use with hierobj-type objects.
+
+Provide for recurse-safe processing. Currently only provide depth-first
+processing, and don't provide means for ignoring branches of the tree
+during processing. For an example of breadth-first processing, see
+mcf.pars.int.index.indutils. For more complex hierarchic processing,
+see the mcf.walker package.
+
+Originally these functions were only methods of the hierobj class (they
+still are methods of it). I've split them out to allow them to be
+imported selectively by other classes (some classes will only want
+the simple walking functions, and not want to be bothered with the
+methods which hierobj uses to keep track of its particular internal
+structures.
+'''
+
+def hier_rapply(self, function,arglist=None,argdict={},moreattr = '__childlist__'):
+ '''
+ Safely apply a function to self and all children for
+ the function's side effects. Discard the return values
+ that function returns.
+
+ function
+ function to apply
+ arglist
+ (self,)+arglist is the set of arguments passed to function
+ argdict
+ passed as namedargs to the function
+ moreattr
+ the attribute representing the children of a node
+ '''
+ alreadydone = {}
+ tobedone = [self]
+ if arglist or argdict:
+ if not arglist: arglist=[self]
+ else:
+ arglist.insert(0,self) # we could insert anything... self is convenient
+ while tobedone:
+ object = tobedone[0]
+ try:
+ alreadydone[id(object)]
+ # We've already processed this object
+ except KeyError:
+ # We haven't processed this object
+ alreadydone[id(object)]=1
+ arglist[0]=object
+ apply(function,tuple(arglist),argdict)
+ try:
+ tobedone[1:1]=getattr(object,moreattr)
+ except AttributeError:
+ # if the object isn't a hierobj, we don't need to recurse into it.
+ pass
+ del(tobedone[0])
+ else: # no arglist or argdict
+ while tobedone:
+ object = tobedone[0]
+ try:
+ alreadydone[id(object)]
+ # We've already processed this object
+ except KeyError:
+ # We haven't processed this object
+ alreadydone[id(object)]=1
+ function(object)
+ try:
+ tobedone[1:1]=getattr(object,moreattr)
+ except AttributeError:
+ # if the object isn't a hierobj, we don't need to recurse into it.
+ pass
+ del(tobedone[0])
+def hier_rreturn(self, function,arglist=None,argdict={},moreattr = '__childlist__'):
+ '''
+ Safely apply a function to self and all children,
+ collect the results in a list and return.
+
+ function
+ function to apply
+ arglist
+ (self,)+arglist is the set of arguments passed to function
+ argdict
+ passed as namedargs to the function
+ moreattr
+ the attribute representing the children of a node
+ '''
+ alreadydone = {}
+ tobedone = [self]
+ results = []
+ if arglist or argdict:
+ if not arglist: arglist=[self]
+ else:
+ arglist.insert(0,self) # or anything you feel like
+ while tobedone:
+ object = tobedone[0]
+ try:
+ alreadydone[id(object)]
+ # We've already processed this object
+ except KeyError:
+ # We haven't processed this object
+ alreadydone[id(object)]=1
+ arglist[0]=object
+ results.append(apply(function,tuple(arglist),argdict))
+ try:
+ tobedone[1:1]=getattr(object,moreattr)
+ except AttributeError:
+ # if the object isn't a hierobj, we don't need to recurse into it.
+ pass
+ del(tobedone[0])
+ else:
+ while tobedone:
+ object = tobedone[0]
+ try:
+ alreadydone[id(object)]
+ # We've already processed this object
+ except KeyError:
+ # We haven't processed this object
+ alreadydone[id(object)]=1
+ results.append(function(object))
+ try:
+ tobedone[1:1]=getattr(object,moreattr)
+ except AttributeError:
+ # if the object isn't a hierobj, we don't need to recurse into it.
+ pass
+ del(tobedone[0])
+ return results
+def hier_rgetattr(self, attrname, multiple=1, moreattr = '__childlist__'):
+ '''
+ Recursively collect the values for attrname and
+ return as a list.
+
+ attrname
+ attribute to collect
+ arglist
+ (self,)+arglist is the set of arguments passed to function
+ argdict
+ passed as namedargs to the function
+ moreattr
+ the attribute representing the children of a node
+ '''
+ alreadydone = {}
+ tobedone = [self]
+ results = []
+ while tobedone:
+ object = tobedone[0]
+ try:
+ alreadydone[id(object)]
+ # We've already processed this object
+ except KeyError:
+ # We haven't processed this object
+ alreadydone[id(object)]=1
+ try:
+ if multiple:
+ results.append(getattr(object, attrname))
+ else:
+ return getattr(object, attrname)
+ except AttributeError:
+ pass
+ try:
+ tobedone[1:1]=getattr(object,moreattr)
+ except AttributeError:
+ # if the object isn't a hierobj, we don't need to recurse into it.
+ pass
+ del(tobedone[0])
+ return results
+def hier_rmethod(self, methodname,arglist=(),argdict={},moreattr = '__childlist__'):
+ '''
+ return the result of calling every object's method methodname,
+ as for hier_rreturn otherwise.
+
+ methodname
+ method to call
+ arglist
+ (self,)+arglist is the set of arguments passed to function
+ argdict
+ passed as namedargs to the function
+ moreattr
+ the attribute representing the children of a node
+ '''
+
+ alreadydone = {}
+ tobedone = [self]
+ results = []
+ while tobedone:
+ object = tobedone[0]
+ try:
+ alreadydone[id(object)]
+ # We've already processed this object
+ except KeyError:
+ # We haven't processed this object
+ alreadydone[id(object)]=1
+ try:
+ results.append(apply(getattr(object,methodname),arglist,argdict))
+ except:
+ pass
+ try:
+ tobedone[1:1]=getattr(object,moreattr)
+ except AttributeError:
+ # if the object isn't a hierobj, we don't need to recurse into it.
+ pass
+ del(tobedone[0])
+ return results
+