6

I'm trying to draw a binary tree using tikz package.

If I use only circle, I get a tree. But I want to represent a subtree using a triangle. Now the tree gets uneven. I want to attach the arrows to the top of the triangle and also want the size of the triangle comparable to the size of the circle.

\documentclass{article}
\usepackage{tikz}
\usepackage{pgfplots}
\pgfplotsset{compat=1.10}
\usetikzlibrary{shapes.geometric,arrows,fit,matrix,positioning}
\tikzset
{
    treenode/.style = {circle, draw=black, align=center, minimum size=1cm},
    subtree/.style  = {isosceles triangle, draw=black, align=center, minimum height=0.5cm, minimum width=1cm, shape border rotate=90, anchor=north}
}
\begin{document}
\begin{figure}[t]
\centering

\caption{An illustration of a simple delete operation. \label{fig:simple}}
{
    \begin{tikzpicture}[->,>=stealth',level/.style={sibling distance = 5cm/#1,
    level distance = 1.5cm},scale=0.6, transform shape]
    \node [treenode] {$X$ \\ 100}
    child
    {
        node [treenode] {$Y$ \\ 50} 
        child
        {
            node [treenode] {$Z$ \\ 40} 
            child
            {
                node [treenode] {$S1$ \\ 30} 
            }
            child
            {
                node [treenode] {$S2$ \\ 60} 
            }
        }
        child
        {
            node [subtree] {$Z$ \\ 200} 
        }
    }
    child
    {
        node [subtree] {$Z$ \\ 200} 
    }
;
    \end{tikzpicture}
}
\end{figure}
\end{document}

output

  • thank you! I'm trying to learn TeX to get a paper written – arunmoezhi Jul 19 '14 at 3:10
5
  1. With the OP's current setting the circles and triangles are of comparable size as long as the text is not written into the subtree nodes. So a possible solution is to write the text later after the drawing is done. This is shown by the last 2 lines of codes.

  2. To have the arrows pointing to the tip of a triangle, the following line is added to the corresponding parent nodes

    edge from parent path ={(\tikzparentnode.-50) -- (\tikzchildnode.north)} % -50 is adjustable.

  3. If the triangles are still incomparable, one can write scale=0.9 into the subtree style for shrinking adjustment.

enter image description here

Code

\documentclass{article}
\usepackage[paper size={10cm,8cm}]{geometry}
\usepackage{tikz}
\usepackage{pgfplots}
\pgfplotsset{compat=newest}
\usetikzlibrary{shapes.geometric,arrows,fit,matrix,positioning}
\tikzset
{
    treenode/.style = {circle, draw=black, align=center, minimum size=1cm},
    subtree/.style  = {isosceles triangle, draw=black, align=center, minimum height=0.5cm, minimum width=1cm, shape border rotate=90, anchor=north}
}
\begin{document}
\begin{figure}[t]
\centering

\caption{An illustration of a simple delete operation. \label{fig:simple}}
{
    \begin{tikzpicture}[->,>=stealth', level/.style={sibling distance = 5cm/#1, level distance = 1.5cm}, scale=0.6,transform shape]
    \node [treenode] {$X$ \\ 100}
    child
    {
        node [treenode] {$Y$ \\ 50} 
        child
        {
            node [treenode] {$Z$ \\ 40} 
            child
            {
                node [treenode] {$S1$ \\ 30} 
            }
            child
            {
                node [treenode] {$S2$ \\ 60} 
            }
        }
        child[edge from parent path ={(\tikzparentnode.-50) -- (\tikzchildnode.north)}]
        {
            node [subtree,yshift=0.4cm] (a) {}   % delay the text till later
        }
    }
    child[edge from parent path ={(\tikzparentnode.-30) -- (\tikzchildnode.north)}]
    {
        node [subtree,yshift=0.4cm] (b) {}       % delay the text till later
    }
;
% ------------------------------------------------ put the text into subtree nodes
\node[align=center,yshift=0.1cm] at (a) {$Z$\\200};
\node[align=center,yshift=0.1cm] at (b) {$Z$\\200};
\end{tikzpicture}
}
\end{figure}
3

The first thing you need to understand for TiKZ nodes is that minimum size means exactly this minimum, i.e., if node contents needs a larger size, TiKZ will take it.

Here you have an example with your treenode and subtree (I've replaced isosceles triangle by an equilater one with regular polygon). As you can see, if node contents is empty, minimum size is respected and there is a relation between circle and triangle size. But as soon as nodes contain some text, their sizes are adapted acordingly.

enter image description here

\documentclass[tikz,border=2mm]{standalone}
\usetikzlibrary{shapes.geometric,arrows,fit,matrix,positioning}
\tikzset
{
    treenode/.style = {circle, draw=black, align=center, minimum size=1cm, anchor=center},
    subtree/.style  = {regular polygon, regular polygon sides=3, draw=black, align=center, minimum size=1cm, anchor=center}
}
\begin{document}
\begin{tikzpicture}
\node[treenode,blue] at (0,0) {};
\node[subtree,red] at (0,0) {};

\node[treenode] at (2,0) {$Y$ \\ 50};
\node[treenode, blue] at (2,0) {};

\node[subtree, inner sep=0pt] at (4,0) {$Y$ \\ 50};
\node[subtree, red, inner sep=0pt] at (4,0) {};
\node[treenode, blue] at (4,0) {};
\end{tikzpicture}
\end{document}

You will have to play with minimum sizes for circular and triangular nodes if you want they present a similar size.

A second problem with your code was anchor=north option in subtree node definition while treenodes had a default anchor=center. Then, top most vertex of subtree was aligned with center point of corresponding treenode.

Your last question was about arrow to north vertex. Use [child anchor=north].

The result could be:

enter image description here

\documentclass[tikz,border=2mm]{standalone}
\usetikzlibrary{shapes.geometric,arrows,fit,matrix,positioning}
\tikzset
{
    treenode/.style = {circle, draw=black, align=center, 
                          minimum size=1cm, anchor=center},
    subtree/.style  = {regular polygon, regular polygon sides=3, 
                          draw=black, align=center, 
                          minimum size=1cm, anchor=center}
}
\begin{document}

    \begin{tikzpicture}[->,>=stealth',level/.style={sibling distance = 5cm/#1,
    level distance = 1.5cm},scale=0.6, transform shape]
    \node [treenode] {$X$ \\ 100}
    child
    {
        node [treenode] {$Y$ \\ 50} 
        child
        {
            node [treenode] {$Z$ \\ 40} 
            child
            {
                node [treenode] {$S1$ \\ 30} 
            }
            child
            {
                node [treenode] {$S2$ \\ 60} 
            }
        }
        child [child anchor=north]
        {
            node [subtree] {$Z$ \\ 200} 
        }
    }
    child [child anchor=north]
    {
        node [subtree] {$Z$ \\ 200} 
    }
;
    \end{tikzpicture}
\end{document}
2

To attach the arrows to the top of the subtrees then saychild[child anchor=apex]

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.