Skip to content

Instantly share code, notes, and snippets.

@jeetsukumaran
Last active March 4, 2016 06:35
Show Gist options
  • Select an option

  • Save jeetsukumaran/011686af2fc8847dbb86 to your computer and use it in GitHub Desktop.

Select an option

Save jeetsukumaran/011686af2fc8847dbb86 to your computer and use it in GitHub Desktop.
# Problem:
# You want to use DendroPy's rich parsing infrastructure to read/write trees,
# but you have your own classes of Trees/Nodes that you want to use.
# Solution:
# Don't just derive from DendroPy's Node/Tree/TreeList class, but at each
# level, specify the appropriate type and/or factory function for the
# component types.
# Derive from dendropy.Node, delegating most work there,
# just adding stuff you want here
class PhyloNode(dendropy.Node):
def __init__(self, *args, **kwargs):
dendropy.Node.__init__(self, *args, **kwargs)
def _get_clades(self):
return self.child_nodes()
clades = property(_get_clades)
def _get_branch_length(self):
return self.edge.length
branch_length = property(_get_branch_length)
# Your custom trees must be composed of your custom Nodes.
# Derive from dendropy.Tree to let it do most of the work,
# including parsing/reading/writing, but make sure to
# override the ``node_factory`` class function to return
# the custom Node-types, in addition to adding extra
# functionality that you want.
class PhyloTree(dendropy.Tree):
@classmethod
def node_factory(cls, *args, **kwargs):
return PhyloNode(*args, **kwargs)
def get_nonterminals(self, order):
if order == "postorder":
return list(self.postorder_internal_node_iter())
else:
raise ValueError(order)
def get_terminals(self):
return list(self.leaf_node_iter())
# Again, override the factories to return your
# classes instead of the native DendroPy ones.
# There are actually two ways to go about
# this. You can simply set the class-level
# variable ``DEFAULT_TREE_TYPE`` if the
# constructor signature is the same as the
# native dendropy.Tree. Otherwise, you can
# override the ``tree_factory`` class
# function. As a special case, you can
# actually create custom tree on a
# per-instance basis, by setting the
# dendropy.TreeList.tree_type instance variable.
class PhyloTreeList(dendropy.TreeList):
DEFAULT_TREE_TYPE = PhyloTree
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment