6

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

  • Welcome! There's nothing to say that you 'should' use TikZ. You could do it in TikZ, although it is arguably overkill. – cfr Jan 19 '16 at 13:29
  • Don't use tikz. Embrace SVG. See: https://tex.stackexchange.com/questions/2099/how-to-include-svg-diagrams-in-latex#2107 – Burak Arslan Jan 19 '16 at 21:52

5 Answers5

13

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

MickG
  • 5,426
ScheRas
  • 131
9

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}
Torbjørn T.
  • 206,688
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

cfr
  • 198,882
  • 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
  • @Zarko True. But it was overkill qua answer to the original question ;). – cfr Jan 19 '16 at 17:16
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

Alenanno
  • 37,338
6
\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