Code Monkey home page Code Monkey logo

anytree's Introduction

https://img.shields.io/pypi/dm/anytree.svg?label=pypi%20downloads https://readthedocs.org/projects/anytree/badge/?version=latest https://readthedocs.org/projects/anytree/badge/?version=stable Maintainability https://img.shields.io/badge/linter-pylint-%231674b1?style=flat https://img.shields.io/badge/PRs-welcome-brightgreen.svg?style=flat-square

Links

https://github.com/c0fec0de/anytree/raw/devel/docs/static/buymeacoffee.png

Getting started

Usage is simple.

Construction

>>> from anytree import Node, RenderTree
>>> udo = Node("Udo")
>>> marc = Node("Marc", parent=udo)
>>> lian = Node("Lian", parent=marc)
>>> dan = Node("Dan", parent=udo)
>>> jet = Node("Jet", parent=dan)
>>> jan = Node("Jan", parent=dan)
>>> joe = Node("Joe", parent=dan)

Node

>>> print(udo)
Node('/Udo')
>>> print(joe)
Node('/Udo/Dan/Joe')

Tree

>>> for pre, fill, node in RenderTree(udo):
...     print("%s%s" % (pre, node.name))
Udo
├── Marc
│   └── Lian
└── Dan
    ├── Jet
    ├── Jan
    └── Joe

For details see Node and RenderTree.

Visualization

>>> from anytree.exporter import UniqueDotExporter
>>> # graphviz needs to be installed for the next line!
>>> UniqueDotExporter(udo).to_picture("udo.png")

https://anytree.readthedocs.io/en/latest/_images/udo.png

The UniqueDotExporter can be started at any node and has various formatting hookups:

>>> UniqueDotExporter(dan,
...                   nodeattrfunc=lambda node: "fixedsize=true, width=1, height=1, shape=diamond",
...                   edgeattrfunc=lambda parent, child: "style=bold"
... ).to_picture("dan.png")

https://anytree.readthedocs.io/en/latest/_images/dan.png

There are various other Importers and Exporters.

Manipulation

A second tree:

>>> mary = Node("Mary")
>>> urs = Node("Urs", parent=mary)
>>> chris = Node("Chris", parent=mary)
>>> marta = Node("Marta", parent=mary)
>>> print(RenderTree(mary))
Node('/Mary')
├── Node('/Mary/Urs')
├── Node('/Mary/Chris')
└── Node('/Mary/Marta')

Append:

>>> udo.parent = mary
>>> print(RenderTree(mary))
Node('/Mary')
├── Node('/Mary/Urs')
├── Node('/Mary/Chris')
├── Node('/Mary/Marta')
└── Node('/Mary/Udo')
    ├── Node('/Mary/Udo/Marc')
    │   └── Node('/Mary/Udo/Marc/Lian')
    └── Node('/Mary/Udo/Dan')
        ├── Node('/Mary/Udo/Dan/Jet')
        ├── Node('/Mary/Udo/Dan/Jan')
        └── Node('/Mary/Udo/Dan/Joe')

Subtree rendering:

>>> print(RenderTree(marc))
Node('/Mary/Udo/Marc')
└── Node('/Mary/Udo/Marc/Lian')

Cut:

>>> dan.parent = None
>>> print(RenderTree(dan))
Node('/Dan')
├── Node('/Dan/Jet')
├── Node('/Dan/Jan')
└── Node('/Dan/Joe')

Extending any python class to become a tree node

The entire tree magic is encapsulated by NodeMixin add it as base class and the class becomes a tree node:

>>> from anytree import NodeMixin, RenderTree
>>> class MyBaseClass(object):  # Just an example of a base class
...     foo = 4
>>> class MyClass(MyBaseClass, NodeMixin):  # Add Node feature
...     def __init__(self, name, length, width, parent=None, children=None):
...         super(MyClass, self).__init__()
...         self.name = name
...         self.length = length
...         self.width = width
...         self.parent = parent
...         if children:
...             self.children = children

Just set the parent attribute to reflect the tree relation:

>>> my0 = MyClass('my0', 0, 0)
>>> my1 = MyClass('my1', 1, 0, parent=my0)
>>> my2 = MyClass('my2', 0, 2, parent=my0)
>>> for pre, fill, node in RenderTree(my0):
...     treestr = u"%s%s" % (pre, node.name)
...     print(treestr.ljust(8), node.length, node.width)
my0      0 0
├── my1  1 0
└── my2  0 2

The children can be used likewise:

>>> my0 = MyClass('my0', 0, 0, children=[
...     MyClass('my1', 1, 0),
...     MyClass('my2', 0, 2),
... ])
>>> for pre, fill, node in RenderTree(my0):
...     treestr = u"%s%s" % (pre, node.name)
...     print(treestr.ljust(8), node.length, node.width)
my0      0 0
├── my1  1 0
└── my2  0 2

Documentation

Please see the Documentation for all details.

Installation

To install the anytree module run:

pip install anytree

If you do not have write-permissions to the python installation, try:

pip install anytree --user

anytree's People

Contributors

bewing avatar c0fec0de avatar cinek810 avatar davidepastore avatar eckp avatar fefnut avatar jkbgbr avatar kmosiejczuk avatar knowsuchagency avatar kylewhite21 avatar laurent-laporte-pro avatar lkundrak avatar lluissalord avatar moi90 avatar paper42 avatar paulo-monteiro avatar salkinium avatar stevenlimpert avatar teauxfu avatar tsvi avatar wimglenn avatar xu-kai-xu avatar zegervdv avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

anytree's Issues

"self.path" attribute is incomplete in "Node._post_attach" definition slot.

Hi,

The self.path attribute is incomplete when accessed from the Node._post_attach definition slot:

from anytree import Node

class MyNode(Node):
    def __init__(self, name, parent=None, **kwargs):
        super(MyNode, self).__init__(name, parent, **kwargs)

    def _post_attach(self, parent):
        print(self.parent)
        print(self.path)


node_a = MyNode('A')
node_b = MyNode('B', node_a)
node_c = MyNode('C', node_b)
node_d = MyNode('D', node_c)

print(node_d.path)
None
(MyNode('/B'),)
None
(MyNode('/C'),)
None
(MyNode('/D'),)
(MyNode('/A'), MyNode('/A/B'), MyNode('/A/B/C'), MyNode('/A/B/C/D'))

This is surprising from an API usage perspective as you would expect self.parent and self.path to be representing the state of the given node after being parented. It would probably worth defining what attaching exactly means.

Cheers,

Thomas

Feature Request: leaves attribute for Node objects

I'm sorry if I'm overlooking a more obvious and better way to do this, but when I want to find all of the leaves of a node I have been using a list comprehension like this:

leaves = [node for node in root.descendants if node.is_leaf]

and it seems like it would be a nice feature to be able to do this:

leaves = root.leaves

Thanks for all your work on this very useful package!

Inconsistent state after LoopError

If a node's parent is changed, the node will be detached (i.e. its parent's children list is updated), but the parent of the corresponding node remains unchanged; if the __check_loop method now raises a LoopError which is captured, the tree becomes inconsistent and the node cannot be re-attached to its previous parent because of lines 102 to 104 in node.py:

        elif parent is not value:
            # detach, check_loop, attach ...
        else:
            # keep parent
            pass

Therefore, I suggest to add the following line to node.py:

elif parent is not value:
     # change parent node
     self.__detach(parent)
     # reset parent
     self._parent = None
     self.__check_loop(value)
     self.__attach(value)

Like this, a node has a defined parent after it has been detached, even if an error occurred.

Even more elegant would be

elif parent is not value:
     # reset parent
     self.parent = None
     self.__check_loop(value)
     self.__attach(value)

However, the former solution can be implemented in a non-intrusive way by modifying _post_detach.

Create tree from list of indented strings

Hi,

I am using anytree to generate a tree-view of pytest hooks based on a log file with indented hooks. pytest-dev/pytest#3261

For that I needed to create a function to convert a list of indented strings to a tree. Apparently another users on stackoverflow have needed it:
https://codereview.stackexchange.com/questions/176391/parsing-indented-text-and-inserting-its-data-into-a-tree
https://stackoverflow.com/questions/17858404/creating-a-tree-deeply-nested-dict-from-an-indented-text-file-in-python
https://stackoverflow.com/questions/32101253/converting-a-string-to-a-tree-structure-in-python?rq=1

I have created the following script for doing this and it is quite simple:
https://github.com/Sup3rGeo/pytest/blob/master/doc/pytesthooks.py

I believe it makes sense to make this part of anytree as a "indented strings importer".

So if you agree I would gladly add a pull request for this. Thanks!

Dotexporter.to_picture does not work on Windows

I might not have done this correctly (submitting an issue and pull request) as it is my first time using github. Let me know if I need to fix anything!

On Windows, the current "to_picture" function does not work as the temporary file name is not visible to the system. Therefore, calling "dot" on the command line will result in a FileNotFoundError.

The fix changes the function so that on windows/cygwin, the file is not deleted until after the picture is made. Once the picture is made, the file in unlinked.

Can't export Node Object in Python3

I find that I can only export Node object with Exporter in Python2. In Python3, however, I can only export AnyNode Object with Exporter and when I export Node Object, it shows 'Node' object does not support indexing.

I hope you can fix it. Thanks!

Iterators can not be used with next()

When using the iterators for the tree objects, I realized that Python (2.7.13) does not recognize them as iterators, presumably because there is no __next__() method:

>>> my_node1, my_node2, my_node3 = Node("a"), Node("b"), Node("c")
>>> my_node2.parent = my_node1
>>> my_iter = tree_iter.PreOrderIter(my_node1)
>>> next(my_iter)
Traceback (most recent call last):
      ...
TypeError: PreOrderIter object is not an iterator

Instead, I have to wrap it in iter() to work:

>>> my_iter = iter(tree_iter.PreOrderIter(my_node1))
>>> next(my_iter)
Node('/a')

Is this intended behavior?

Import data

It would be great to be able to import dot files (or other formats) in addition to export

Naming of the "detach" and "attach" slots.

Hi,

I wanted to start talking about the current naming convention of the detach and attach slots:

  • _pre_detach
  • _post_detach
  • _pre_attach
  • _post_attach

In theory and accordingly to PEP 8, the fact they start with an underscore implies for seasoned Python developers that they are part of the recognised private part of the API:

Use one leading underscore only for non-public methods and instance variables.

This is not a major problem but it makes me a bit uncomfortable.

As a side note last week when we were discussing about some of work I have done leveraging anytree, a co-worker asked me why the _pre_detach definitions in my code were named like so, told him I could not do much about it and it was the way anytree was exposing the hooks.

I reckon that it would be great to name them in a way that it is clear that they are part of the public API of anytree.

Setting a node's children simultaneously

I find it sometimes useful to set the children of a node simultaneously all in one step. This is motivated by trees--or, more precisely, their interpretation--that can be invalidated by adding children sequentially; however, in order to check whether a particular set of children would result in a valid tree, I need to be able to add all children at once. Therefore, I extended this class by a setter method for the children attribute, as well as hooks _pre_detach_children, _post_detach_children, _pre_attach_children, and _post_attach_children. Any interest in incorporating this?

Allow undirected graphs in anytree.dotexport

It would be nice to be able to use RenderTreeGraph(root, graph='graph') so that it replaces the -> for a -- in anytree.dotexport at function __iter_edges.
Currently it causes DOT to give back a syntax error and I would like to render undirected graphs as well.

"AttributeError" exception raised when accessing instantiation time "kwarg" in attach callbacks.

Hi,

An AttributeError exception is being raised when I try to access an instantiation time kwarg in the attach callbacks.

Here is a reproducible example:

from anytree import Node

class MyNode(Node):
    def __init__(self, name, parent=None, **kwargs):
        super(MyNode, self).__init__(name, parent, **kwargs)

    def _post_attach(self, parent):
        print(self.my_attribute)


node_a = MyNode('A')
node_b = MyNode('B', node_a, my_attribute=True)
print(node_b)

and the traceback:

AttributeErrorTraceback (most recent call last)
<ipython-input-22-94f8f5bf82a3> in <module>()
     12 
     13 node_a = MyNode('A')
---> 14 node_b = MyNode('B', node_a, my_attribute=True)
     15 print(node_b)

<ipython-input-22-94f8f5bf82a3> in __init__(self, name, parent, **kwargs)
      5 class MyNode(AbstractNode):
      6     def __init__(self, name, parent=None, **kwargs):
----> 7         super(MyNode, self).__init__(name, parent, **kwargs)
      8 
      9     def _post_attach(self, parent):

<ipython-input-18-7c2ada3c82ac> in __init__(self, name, parent, **kwargs)
      8             kwargs['attribute'] = True
      9 
---> 10         super(AbstractNode, self).__init__(name, parent, **kwargs)
     11 
     12 class ConcreteNode(AbstractNode):

C:\Users\thomas\Packages\anytree\2.2.1\anytree\Lib\site-packages\anytree\node.pyc in __init__(self, name, parent, **kwargs)
    429         """
    430         self.name = name
--> 431         self.parent = parent
    432         self.__dict__.update(kwargs)
    433 

C:\Users\thomas\Packages\anytree\2.2.1\anytree\Lib\site-packages\anytree\node.pyc in parent(self, value)
    100             self.__check_loop(value)
    101             self.__detach(parent)
--> 102             self.__attach(value)
    103         else:
    104             # keep parent

C:\Users\thomas\Packages\anytree\2.2.1\anytree\Lib\site-packages\anytree\node.pyc in __attach(self, parent)
    128         assert self not in parentchildren, "Tree internal data is corrupt."
    129         parentchildren.append(self)
--> 130         self._post_attach(parent)
    131 
    132     @property

<ipython-input-22-94f8f5bf82a3> in _post_attach(self, parent)
      8 
      9     def _post_attach(self, parent):
---> 10         print(self.my_attribute)
     11 
     12 

AttributeError: 'MyNode' object has no attribute 'my_attribute'

The reason is because Node.__dict__ gets updated only after accessing the Node.parent property here:

https://github.com/c0fec0de/anytree/blob/master/anytree/node.py#L432

Moving the statement before fixes the issue.

No iterator attribute when importing anytree

Hi everyone, I'm using AnyTree in an independent environment where there is no pip.

I started by moving the anytree folders to the required folders, and started getting import error for six. I downloaded six and placed it in as well, and now I get:

'module' object has no attribute 'iterator'

In case anyone is interested - this is the code for doing this without pip:

from os import sys

sys.path.insert(0, "C:\Program Files (x86)\SmartBear\TestComplete 12\Bin\Extensions\Python\Python34\Lib\site-packages")

import six
import anytree

udo = Node("Udo")
print(udo)

Any ideas on how to fix this? If this isn't related to AnyTree sorry for wasting your time - google only returned this result: https://stackoverflow.com/questions/25612946

DotExporter on Windows OS cannot create a graph plot

Windows 8.1 (64 bit)
graphviz 2.38.0
Python 2.7.15 (32 bit)
anytree 2.4.3

>dot -v dot - graphviz version 2.38.0 (20140413.2041) libdir = "C:\Program Files (x86)\Graphviz2.38\bin" Activated plugin library: gvplugin_dot_layout.dll Using layout: dot:dot_layout Activated plugin library: gvplugin_core.dll Using render: dot:core Using device: dot:dot:core The plugin configuration file: C:\Program Files (x86)\Graphviz2.38\bin\config6 was successfully loaded. render : cairo dot fig gd gdiplus map pic pov ps svg tk vml vrml xdot layout : circo dot fdp neato nop nop1 nop2 osage patchwork sfdp twopi textlayout : textlayout device : bmp canon cmap cmapx cmapx_np dot emf emfplus eps fig gd gd2 gif gv imap imap_np ismap jpe jpeg jpg metafile pdf pic plain plain-ext png pov ps ps2 svg svgz tif tiff tk vml vmlz vrml wbmp xdot xdot1.2 xdot1.4 loadimage : (lib) bmp eps gd gd2 gif jpe jpeg jpg png ps svg

python anytree_picture_export.py
`from anytree import Node, RenderTree
from anytree.exporter import DotExporter

udo = Node("Udo")
marc = Node("Marc", parent=udo)
lian = Node("Lian", parent=marc)
dan = Node("Dan", parent=udo)
jet = Node("Jet", parent=dan)
jan = Node("Jan", parent=dan)
joe = Node("Joe", parent=dan)

DotExporter(udo).to_picture("udo.png")`

I am trying to produce a graph plot with anytree (see code above) and getting the following error:

>python anytree_picture_export.py Error: dot: can't open c:\users\user\appdata\local\temp\tmpvdgutg Traceback (most recent call last): File "anytree_picture_export.py", line 12, in <module> DotExporter(udo).to_picture("udo.png") File "C:\Python27\lib\site-packages\anytree\exporter\dotexporter.py", line 229, in to_picture check_call(cmd) File "C:\Python27\lib\subprocess.py", line 190, in check_call raise CalledProcessError(retcode, cmd) subprocess.CalledProcessError: Command '['dot', 'c:\\users\\user\\appdata\\local\\temp\\tmpvdgutg', '-T', 'png', '-o', 'udo.png']' returned non-zero exit status 2

I tried to change the file format to "pdf" and "jpg" with the same error message. Stepping through the DotExporter, the temporary file dotfile is created and the dot lines are written correctly, yet there seems to be a problem with file permission or handling.

FileNotFoundError: [WinError 2] The system cannot find the file specified

I want to use anytree in anaconda in Win10 OS, but when i just run

root = Node("root")
s0 = Node("sub0", parent=root)
s0b = Node("sub0B", parent=s0)
s0a = Node("sub0A", parent=s0)
s1 = Node("sub1", parent=root)
s1a = Node("sub1A", parent=s1)
s1b = Node("sub1B", parent=s1)
s1c = Node("sub1C", parent=s1)
s1ca = Node("sub1Ca", parent=s1c)


RenderTreeGraph(root).to_picture("tree.png")

I get error like this

runfile('C:/Users/NWPU/.spyder-py3/temp.py', wdir='C:/Users/NWPU/.spyder-py3')
Traceback (most recent call last):

  File "<ipython-input-12-2380dbac90f7>", line 1, in <module>
    runfile('C:/Users/NWPU/.spyder-py3/temp.py', wdir='C:/Users/NWPU/.spyder-py3')

  File "C:\ProgramData\Anaconda3\lib\site-packages\spyder\utils\site\sitecustomize.py", line 710, in runfile
    execfile(filename, namespace)

  File "C:\ProgramData\Anaconda3\lib\site-packages\spyder\utils\site\sitecustomize.py", line 101, in execfile
    exec(compile(f.read(), filename, 'exec'), namespace)

  File "C:/Users/NWPU/.spyder-py3/temp.py", line 42, in <module>
    RenderTreeGraph(root).to_picture("tree.png")

  File "C:\ProgramData\Anaconda3\lib\site-packages\anytree\exporter\dotexporter.py", line 229, in to_picture
    check_call(cmd)

  File "C:\ProgramData\Anaconda3\lib\subprocess.py", line 286, in check_call
    retcode = call(*popenargs, **kwargs)

  File "C:\ProgramData\Anaconda3\lib\subprocess.py", line 267, in call
    with Popen(*popenargs, **kwargs) as p:

  File "C:\ProgramData\Anaconda3\lib\site-packages\spyder\utils\site\sitecustomize.py", line 209, in __init__
    super(SubprocessPopen, self).__init__(*args, **kwargs)

  File "C:\ProgramData\Anaconda3\lib\subprocess.py", line 709, in __init__
    restore_signals, start_new_session)

  File "C:\ProgramData\Anaconda3\lib\subprocess.py", line 997, in _execute_child
    startupinfo)

FileNotFoundError: [WinError 2] 系统找不到指定的文件。

could somebody help me out?

global name 'findall' is not defined

I got an error findall not defined. i already import Ascii
and im using Python 2.7
here is my code

from anytree import Node, RenderTree, AsciiStyle, LevelOrderIter

def buildTree(dataset):
	root = Node("root")

	for data in dataset:
		parent = 0;
		for item in data:
			if parent==0:
				parent = root

			findall(parent, filter_=lambda node: node.name in ("a", "b"))	
			parent = Node(item, parent=parent, support = 1)

	for pre, fill, node in RenderTree(root):
		print("%s%s" % (pre, node.name))

here is the error

Traceback (most recent call last):
  File "C:\Users\Kevin\PycharmProjects\AqeelaTugasAkhir\index.py", line 83, in <module>
    tree = buildTree(itemOrdered)
  File "C:\Users\Kevin\PycharmProjects\AqeelaTugasAkhir\index.py", line 60, in buildTree
    findall(parent, filter_=lambda node: node.name in ("a", "b"))
NameError: global name 'findall' is not defined

What's wrong with findall?
thanks for help

Works and does not work in an python notebook (anaconda 3)

Hallo,
Just busy programming an Binary puzzle solver.
What works: creating the nodes of the search tree for a solution works fine directly.
But if i put the commands in a def ... The nodes are not to be found in command alinea of the notebook.
It is probably my missing knowledge of ... How to get the nodes accessibke out of the function ..
Help is apreciated

Cannot export .png file

from anytree import Node, RenderTree
from anytree.exporter import DotExporter
import graphviz

udo = Node("Udo")
marc = Node("Marc", parent=udo)

DotExporter(udo).to_picture("C:\Users\Simonas\udo.png")

this yields error:

error

Rearranging the tree

I'm using in one of my current projects the NodeMixin class and I quite enjoy the simple way it works. I very much appreciate the work put in the module.
I wonder if it would be possible to extend the package to enable defining two - or possibly more - "parallel" trees from the same set of nodes to account for different logics in the nodes.
Think: all people in the world can be ordered in a family tree on a pure "biological" basis but also like "real" parents - who grew who up. Not necessarily the best example but I hope you get the point.
Current implementation uses the parent attribute as a keyword to define the parent-child relations. Would it be possible to change this to a configurable keyword and - naive thinking, without really knowing and/or having studied the inner workings of the module - use mostly getattr-setattr to do the job?

Assertion wrongly uses __eq__ for testing membership in children list

Hi,
In my application I have a Mapping type that is also a NodeMixin. Since the Mapping redefines eq to be key-wise comparison the following assertion gets triggered when two sibling nodes have the same keys and values:
assert self in parentchildren, "Tree internal data is corrupt."

I attached a diff to change this to use object identity comparison:
assert any(x is self for x in parentchildren), "Tree internal data is corrupt."

Best,
Bob
assert.diff.txt

RenderTreeGraph Image Size

Hey,

My image output generated by RenderTreeGraph is looking a bit squished.

Any way to change the image size?

sorting when rendering a tree

Awesome project !!

I was wondering if there are any way to sort the children when rendering a tree ? For example let's say I'd like the children to be sorted by name (or by attribute, ...), I could pass a sorting callback function to RenderTree that would sort them similarly to what sorted does with key.

Thanks

No module named exporter

When trying to use DotExporter to generate PNG's on Mac OS 10.12.6:

>>> from anytree.exporter import DotExporter
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ImportError: No module named exporter
Name: anytree
Version: 2.2.2
Name: graphviz
Version: 0.8.1

Plans to persist tree to file and create a tree from file?

First of all, amazing work in here. I'm planing to use anytree to a huge kind of backtracking implementation. I will need to persist the tree to a file at some point, and of course, get the tree back from a file.

Are you planning to do it? Is it possible? Should i give it a try and then send the pull request?

Thank you

RenderTree output in wxPython TextCtrl

Probably not an anytree issue, but perhaps someone already had the same experience.
I use wxPython's TextCtrl to render my Anytree object. Everything renders nice except for the percent signs. In the example below each "115428736n" (a hash maybe?) stands / should stand for the percent sign.

Any idea what this might be and how to fix it?

08:23:22: └── results
08:23:22: ├── 41 115428736n BF1 für Head crown, serf = 3.94 ≤ SheetThickness, 10 NW (9.5 MW).
08:23:22: ├── 60 115428736n BF1 für Head knuckle, serf = 5.75 ≤ SheetThickness, 10 NW (9.5 MW).

Printing a node of non-str type

Currently, the __repr__ function for printing node expects all the arguments to of type str.
However, I think a general construct which can print a node independent of it's type is more suitable.

Here is how I encountered this bug:

In []: a = [1, 2, 3]
In []: me = Person('Kshitij', 20) # some user defined class
In []: myroot = Node(a)
In []: leaf = Node(b, parent=myroot)
In []: print(myroot)
---------------------------------------------------------------------------
TypeError                                 Traceback (most recent call last)
<ipython-input-23-fd64928be722> in <module>()
----> 1 print(myroot)

/usr/local/lib/python3.5/dist-packages/anytree/__init__.py in __repr__(self)
    376     def __repr__(self):
    377         classname = self.__class__.__name__
--> 378         args = ["%r" % "/".join([node.name for node in self.path])]
    379         for key, value in filter(lambda item: not item[0].startswith("_"),
    380                                  sorted(self.__dict__.items(),

TypeError: sequence item 0: expected str instance, list found

In[]: for pre, fill, node in RenderTree(myroot):
          print('{}{}'.format(pre, node.name))
[1, 2, 3]
└── Person(name='Kshitij', age=20)

Document Usage of Non-String Nodes

Currently, the documentation only shows initializing Node using a string. However, it isn't clear whether strings are required. For example, I'm interested in creating a tree out of enumerated type values. But I get a variety of strange behavior when trying to do that.

Add hierarchy wildcard `**` to Resolver.glob()

Version 2.1.1 - glob returns only the closest children:

d = Node("parent")
child_1 = Node("child_1", parent=d, value="5")
child_2 = Node("child_2", parent=d, value="5")
grandson_1 = Node("child_1", parent=child_1, value="5")
grandson_2 = Node("child_1", parent=child_1, value="5")
r = Resolver("value")
nodes = r.glob(d, "5")

Will return only child_1 and child_2

Adding Node description to DotExporter.to_picture()

How can we display Node descriptions that has been set beforehand in DotExporter.to_picture() ?

In my case my nodes was initialised with Node("A", task="task A"), I want the task to be displayed under the node name. Something like this:

+--------+
|      A |
|  task A|
+--------+

scalability

I guess there are some scalability issue with anytree due to the linear search in most(all?) of the find operations.
A tree with 3 million nodes takes about 30-45 minutes to create compared to couple of seconds with just dict(of dicts)
i guess 'insert a child a node if no child node exists' gets slowed down due to the linear search of child nodes.

Installation issue on Python 3.5.2

Could be an anaconda bug or something, this is the output I get:

Collecting anytree
Downloading anytree-2.4.3.tar.gz
Complete output from command python setup.py egg_info:
Traceback (most recent call last):
File "", line 1, in
File "/tmp/pip-build-pwc646vg/anytree/setup.py", line 6, in
from setuptools import setup
ImportError: cannot import name 'setup'

For Python

symbolic links

is it possible to have some kind of of support for symbolic links where a node can point/link to another part of the tree?

Limit substree depth in export

It would be great if it were possible to pass options to PreOrderIter in the exporter. Concretely, I'd like to limit the depth of the exported subtree, and it should be easy if it were posisble to hand-down a "maxlevel" option to PreOrderIter (I think). But since that is hard-coded, that is not trivial to do.

Would that make sense?

glob doesn't work for same attribute value nodes

Since __get_nodemap returns OrderedDict, it requires that the search by part will be unique, and hence doesn't allow searching for more than one node with the same value.

E.g.

d = Node("parent")
child_1 = Node("child_1", parent=d, value="5")
child_2 = Node("child_2", parent=d, value="5")
r = Resolver("value")
nodes = r.glob(d, "5")

will return only the last found node.

Error installing with python 3.4

Hi!

I have an issue installing anytree on py34 (also 3.3, but I don't think it is supported) in a virtualenv using tox.

Collecting anytree (from pymenu==0.1.0)
  Downloading anytree-2.2.0.tar.gz
    Complete output from command python setup.py egg_info:
    Traceback (most recent call last):
      File "<string>", line 1, in <module>
      File "/tmp/pip-build-q22xz5l_/anytree/setup.py", line 24, in <module>
        config = _read_metainfo("anytree/__init__.py")
      File "/tmp/pip-build-q22xz5l_/anytree/setup.py", line 18, in _read_metainfo
        match = pat.match(line)
    TypeError: can't use a string pattern on a bytes-like object

You can see it on my travis build:

https://travis-ci.org/cblegare/pymenu/jobs/239447205

Search Function

I think that a search function should be added to this module. It will search in all the nodes and then return the path of all the nodes (as a list) which match the given text. I have already made this function, I would like to contribute to this module.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.