4

I want to draw two doubly linked lists and I know that I can use the tikz package. But I don't know how to. Could anyone show an example code piece for the following doubly linked list?

I found some questions that are related to drawing doubly linked lists, e.g., How should I draw a singly/double linked list?. But I don't how to draw the "..." in the figure.

enter image description here

9

Arguably overkill, but here's a version using the TikZ libraries shapes.multipart, chains and positioning:

\documentclass[border=20pt,tikz]{standalone}
\usetikzlibrary{shapes.multipart,chains, positioning}
\begin{document}
\begin{tikzpicture}
    [
      double link/.style n args=2{% page 726
        on chain,
        rectangle split,
        rectangle split horizontal,
        rectangle split parts=2,
        draw,
        anchor=center,
        text height=1.5ex,
        node contents={#1\nodepart{two}#2},
      },
      start chain=going right,
    ]
    \node [on chain] {$\phi$};
    \node [join={by <-}, double link={a}{b}];
    \node [join={by <->}, double link={c}{d}];
    \node (a) [join={by <->}, double link={e}{f}];
    \node (b) [on chain, right=2.5pt of a.east] {$\cdots$};
    \node [double link={y}{z}, right=2.5pt of b.east];
    \node [join={by ->}, on chain] {$\phi$};
\end{tikzpicture}
\end{document}

double trouble

EDIT

In response to the comment asking about the addition of arcs, there are various options. Here are 4 different arcs in various colours for ease of identification. To please egreg, I assume that the thing which I read as the Greek letter phi is, in fact, intended to be an empty set.

\documentclass[border=20pt,tikz]{standalone}
\usetikzlibrary{shapes.multipart,chains, positioning}
\begin{document}
\begin{tikzpicture}
    [
      double link/.style n args=2{% page 726
        on chain,
        rectangle split,
        rectangle split horizontal,
        rectangle split parts=2,
        draw,
        anchor=center,
        text height=1.5ex,
        node contents={#1\nodepart{two}#2},
      },
      start chain=going right,
    ]
    \node [on chain] {$\emptyset$};
    \node (c) [join={by <-}, double link={a}{b}];
    \node [join={by <->}, double link={c}{d}];
    \node (a) [join={by <->}, double link={e}{f}];
    \node (b) [on chain, right=2.5pt of a.east] {$\cdots$};
    \node [join={with c by <->, bend right, draw=blue}, join={with c by <->, bend left, draw=green}, join={with c by <->, out=90, in=90, draw=red}, join={with c by <->, out=-135, in=-45, draw=magenta}, double link={y}{z}, right=2.5pt of b.east];
    \node [join={by ->}, on chain] {$\emptyset$};
\end{tikzpicture}
\end{document}

arcs of various kinds

  • Thanks a lot! By the way, is it possible to create an arc between {a, b} and {y, z} ? – addddddc Jan 19 '16 at 14:14
  • 1
    \emptyset \neq \phi – egreg Jan 19 '16 at 14:34
  • 1
    @egreg I just went by the drawing. I guess I'm much more likely to see phi than an empty set symbol. Since I never read anything including the latter, but frequently read stuff including the former, I guess I assume the former is intended in case of ambiguity. – cfr Jan 19 '16 at 15:22
  • @addddddc Please see edit. Also, if the symbol at the ends is supposed to be an empty set, you shouldn't use \phi. On the other hand, if it is supposed to be the Greek letter phi, then you should use \phi. Horses for courses, as they say ;). – cfr Jan 19 '16 at 15:34
  • (+1) @cfr, with this additional request, your solution is not "overkill" solution anymore :-), actually it is the most rational! – Zarko Jan 19 '16 at 16:29
9

I've found one useful github repository with example of doubly linked list in tikz. You can inspire in this.

Code of the example:

\documentclass{article}
\usepackage[pdftex,active,tightpage]{preview}
\setlength\PreviewBorder{2mm}

\usepackage{tikz}
\usetikzlibrary{calc,shapes.multipart,chains,arrows,positioning}

\tikzset{
    squarecross/.style={
        draw, rectangle,minimum size=18pt, fill=orange!80,
        inner sep=0pt, text=black,
        path picture = {
            \draw[black]
            (path picture bounding box.north west) --
            (path picture bounding box.south east)
            (path picture bounding box.south west) --
            (path picture bounding box.north east);
        }
    }
}

\begin{document}
\begin{preview}
\begin{tikzpicture}[
        list/.style={
            very thick, rectangle split,
            rectangle split parts=3, draw,
            rectangle split horizontal, minimum size=18pt,
            inner sep=5pt, text=black,
            rectangle split part fill={blue!20, red!20, blue!20}
        },
        ->, start chain, very thick
      ]

  \node[list,on chain] (A) {\nodepart{second} 12};
  \node[list,on chain] (B) {\nodepart{second} 99};
  \node[list,on chain] (C) {\nodepart{second} 37};

  \node[squarecross]   (D) [right=of C] {};
  \node[squarecross]   (E) [left= of A] {};

  \path[*->] let \p1 = (A.three), \p2 = (A.center) in (\x1,\y2) edge [bend left] ($(B.one)+(0,0.2)$);
  \path[*->] let \p1 = (B.three), \p2 = (B.center) in (\x1,\y2) edge [bend left] ($(C.one)+(0,0.2)$);
  \draw[*->] let \p1 = (C.three), \p2 = (C.center) in (\x1,\y2) -- (D);

  \draw[*->] ($(A.one)+(0.2,0.1)$) -- (E);
  \path[*->] ($(B.one)+(0.1,0.1)$) edge [bend left] ($(A.three)+(0,-0.05)$);
  \path[*->] ($(C.one)+(0.1,0.1)$) edge [bend left] ($(B.three)+(0,-0.05)$);
\end{tikzpicture}
\end{preview}
\end{document}

Output:

enter image description here

  • 5
    Welcome to TeX.SE. Link only answer are not really useful since the link may vanish ;-) – Romain Picot Jan 19 '16 at 14:00
  • 1
    I'm sorry. Next time better. – ScheRas Jan 19 '16 at 14:39
8

TikZ-free suggestion.

enter image description here

\documentclass{article}
\newcommand\boxlist[2]{\begin{array}{|c|c|} \hline #1 & #2 \\ \hline \end{array}}
\begin{document}
\[
\phi \leftarrow
\boxlist{a}{b}
\leftrightarrow
\boxlist{c}{d}
\leftrightarrow
\boxlist{e}{f}
\leftrightarrow
\cdots
\leftrightarrow
\boxlist{x}{y}
\rightarrow \phi
\]
\end{document}
8

A short example with tikz-cd and some TikZ for drawing the node border.

Output

enter image description here

Code

\documentclass{article}
\usepackage{tikz-cd}
\usepackage{amssymb}

\newcommand\tkkz[2]{%
  \tikz{\node[draw, inner sep=2pt, minimum width=8mm,outer sep=0, text height=1.5ex, text depth=.3ex, append after command={\pgfextra{\draw (\tikzlastnode.north)--(\tikzlastnode.south);}}](a){#1~~#2}}
}

\begin{document}
\begin{tikzcd}
\varnothing \arrow[r,to-] & 
  \tkkz{a}{b} \arrow[r,to-to]&
  \tkkz{c}{d} \arrow[r,to-to]&
  \tkkz{e}{f} \arrow[r,to-to]&
  \cdots \arrow[r,to-] &
  \tkkz{y}{z} \arrow[r] &
\varnothing
\end{tikzcd}
\end{document}

Curved arrows

To draw a curved arrow, just do either of these commands:

\arrow[rrrr, bend left=90]
or
\arrow[rrrr, out=90,in=90]

Each r tells the arrow to advance of a cell to the right, since tikz-cd is basically a matrix of nodes (similar to a tabular). To draw the arrow below, just invert the commands like this:

\arrow[rrrr, bend right=90]
or
\arrow[rrrr, out=-90,in=-90]

With either of those commands to draw the arrow above you get:

enter image description here

5
\documentclass{article}
\let\LA\leftarrow  \let\RA\rightarrow \let\LRA\leftrightarrow
\def\BOX(#1,#2){\tabular{|c|c|}\hline\strut#1&#2\\\hline\endtabular}

\begin{document}

 $\thickmuskip=0mu\emptyset\,
  \LA\BOX(a,b)\LRA\BOX(c,d)\LRA\BOX(e,f)\LRA\cdots\LA\BOX(y,z)\RA\,
  \emptyset$ 

\end{document}

If you want the a,b,... in italic use \array instead of \tabular

enter image description here

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.