summaryrefslogtreecommitdiffstats
path: root/docs/source/index.rst
blob: 2834becbb8ab5c07b9d5db2d4196639c1d254676 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
.. treelib documentation master file, created by
   sphinx-quickstart on Thu Dec 20 16:30:18 2018.
   You can adapt this file completely to your liking, but it should at least
   contain the root `toctree` directive.

Welcome to treelib's documentation!
***********************************

.. toctree::
   :maxdepth: 2
   :caption: Contents:

Introduction
============

`Tree <http://en.wikipedia.org/wiki/Tree_%28data_structure%29>`_ is an
important data structure in computer science. Examples are shown in ML algorithm designs such as random forest tree and software engineering such as file system index. `treelib <https://github.com/caesar0301/pyTree>`_ is created to provide an efficient implementation of tree data structure in Python.

The main features of `treelib` includes:
   * Efficient operation of node searching, O(1).
   * Support common tree operations like **traversing**, **insertion**, **deletion**, **node moving**, **shallow/deep copying**, **subtree cutting** etc.
   * Support user-defined data payload to accelerate your model construction.
   * Pretty tree showing and text/json dump for pretty show and offline analysis.
   * Compatible with Python 2 and 3.

Installation
============

The rapidest way to install treelib is using the package management tools like
``easy_install`` or ``pip`` with command

	.. code-block:: sh

		$ sudo easy_install -U treelib

or the setup script

	.. code-block:: sh

		$ sudo python setup.py install

**Note**: With the package management tools, the hosted version may be falling
behind current development branch on `Github
<https://github.com/caesar0301/pyTree>`_. If you encounter some problems, try
the freshest version on Github or open `issues
<https://github.com/caesar0301/pyTree/issues>`_ to let me know your problem.

Examples
========

Basic Usage
-------------

.. code-block:: sh

    >>> from treelib import Node, Tree
    >>> tree = Tree()
    >>> tree.create_node("Harry", "harry")  # root node
    >>> tree.create_node("Jane", "jane", parent="harry")
    >>> tree.create_node("Bill", "bill", parent="harry")
    >>> tree.create_node("Diane", "diane", parent="jane")
    >>> tree.create_node("Mary", "mary", parent="diane")
    >>> tree.create_node("Mark", "mark", parent="jane")
    >>> tree.show()
    Harry
    ├── Bill
    └── Jane
        ├── Diane
           └── Mary
        └── Mark


API Examples
--------------

**Example 1**: Expand a tree with specific mode (Tree.DEPTH [default],
Tree.WIDTH, Tree.ZIGZAG).

.. code-block:: sh

    >>> print(','.join([tree[node].tag for node in \
                tree.expand_tree(mode=Tree.DEPTH)]))
    Harry,Bill,Jane,Diane,Mary,Mark

**Example 2**: Expand tree with custom filter.

.. code-block:: sh

    >>> print(','.join([tree[node].tag for node in \
                tree.expand_tree(filter = lambda x: \
                x.identifier != 'diane')]))
    Harry,Bill,Jane,Mark

**Example 3**: Get a subtree with the root of 'diane'.

.. code-block:: sh

    >>> sub_t = tree.subtree('diane')
    >>> sub_t.show()
    Diane
    └── Mary

**Example 4**: Paste a new tree to the original one.

.. code-block:: sh

    >>> new_tree = Tree()
    >>> new_tree.create_node("n1", 1)  # root node
    >>> new_tree.create_node("n2", 2, parent=1)
    >>> new_tree.create_node("n3", 3, parent=1)
    >>> tree.paste('bill', new_tree)
    >>> tree.show()
    Harry
    ├── Bill
    │   └── n1
    │       ├── n2
    │       └── n3
    └── Jane
        ├── Diane
           └── Mary
        └── Mark

**Example 5**: Remove the existing node from the tree

.. code-block:: sh

    >>> tree.remove_node(1)
    >>> tree.show()
    Harry
    ├── Bill
    └── Jane
        ├── Diane
           └── Mary
        └── Mark

**Example 6**: Move a node to another parent.

.. code-block:: sh

    >>> tree.move_node('mary', 'harry')
    >>> tree.show()
    Harry
    ├── Bill
    ├── Jane
    │   ├── Diane
    │   └── Mark
    └── Mary

**Example 7**: Get the height of the tree.

.. code-block:: sh

    >>> tree.depth()
    2

**Example 8**: Get the level of a node.

.. code-block:: sh

    >>> node = tree.get_node("bill")
    >>> tree.depth(node)
    1

**Example 9**: Print or dump tree structure. For example, the same tree in
 basic example can be printed with 'ascii-em':

.. code-block:: sh

    >>> tree.show(line_type="ascii-em")
    Harry
    ╠══ Bill
    ╠══ Jane
    ║   ╠══ Diane
    ║   ╚══ Mark
    ╚══ Mary

In the JSON form, to_json() takes optional parameter with_data to trigger if
the data field is appended into JSON string. For example,

.. code-block:: sh

    >>> print(tree.to_json(with_data=True))
    {"Harry": {"data": null, "children": [{"Bill": {"data": null}}, {"Jane": {"data": null, "children": [{"Diane": {"data": null}}, {"Mark": {"data": null}}]}}, {"Mary": {"data": null}}]}}

**Example 10**: Save tree into file
  The function save2file require a filename.
  The file is opened to write using mode 'ab'.

.. code-block:: sh

    >>> tree.save2file('tree.txt')


Advanced Usage
----------------

Sometimes, you need trees to store your own data. The newest version of
:mod:`treelib` supports ``.data`` variable to store whatever you want. For
example, to define a flower tree with your own data:

.. code-block:: sh

    >>> class Flower(object): \
            def __init__(self, color): \
                self.color = color

You can create a flower tree now:

.. code-block:: sh

    >>> ftree = Tree()
    >>> ftree.create_node("Root", "root", data=Flower("black"))
    >>> ftree.create_node("F1", "f1", parent='root', data=Flower("white"))
    >>> ftree.create_node("F2", "f2", parent='root', data=Flower("red"))

Printing the colors of the tree:

.. code-block:: sh

    >>> ftree.show(data_property="color")
        black
        ├── white
        └── red

**Notes:** Before version 1.2.5, you may need to inherit and modify the behaviors of tree. Both are supported since then. For flower example,

.. code-block:: sh

    >>> class FlowerNode(treelib.Node): \
            def __init__(self, color): \
                self.color = color
    >>> # create a new node
    >>> fnode = FlowerNode("white")


Indices and tables
==================

* :ref:`genindex`
* :ref:`modindex`
* :ref:`search`