1

I'm trying to visualise a Markov chain and after some research used a matrix with chains. This works quite will, but I can't get to originate and terminate the lines where I want them. Here my code, first the main file:

\documentclass[10pt, conference, letterpaper]{IEEEtran}

\usepackage{tikz}
\usepackage{amsmath}
\usetikzlibrary{arrows,chains,matrix,positioning,scopes,shapes,snakes}
\makeatletter
\tikzset{join/.code=\tikzset{after node path={
\ifx\tikzchainprevious\pgfutil@empty\else(\tikzchainprevious)
edge[every join]#1(\tikzchaincurrent)\fi}}}

\begin{document}
\begin{figure}[h]
\begin{center}
\resizebox{\columnwidth}{!}{
\input{matrix.tikz}
}
\end{center}
\end{figure}
\end{document}

And the tikz file (for some reason it doesn't work in one file):

\begin{tikzpicture}
\tikzset{>=stealth',every on chain/.append style={join},
         every join/.style={->}}
\tikzstyle{labeled}=[execute at begin node=$\scriptstyle,
   execute at end node=$]
\tikzstyle{state}=[ellipse, fill=white,draw=black,thick,text=black,scale=1]
\tikzstyle{stateinv}=[ellipse, fill=white,draw=white,thick,text=black,scale=1]
\tikzstyle{point}=[circle, fill=white,draw=white,thick,text=white,scale=1,inner sep=0pt,minimum size=0]
  \matrix (m) [matrix of nodes, row sep=3em, column sep=3em,nodes={
        anchor=center
    }]
    { |[point]| & |[point]| & |[point]| & |[point]| & |[point]| & |[point]| \\
      |[point]| & |[state]| $0,0$ & |[state]| $0,1$  & $\ldots$  & |[state]| $0,W_0-2$  & |[state]| $0,W_0-1$ \\
      |[point]| & |[stateinv]| \vdots & |[stateinv]| \vdots & |[stateinv]| \vdots & |[stateinv]| \vdots & |[stateinv]| \vdots \\
      [-1cm]
      |[point]| & |[state]| $i,0$ & |[state]| $i,1$  & $\ldots$  & |[state]| $i,W_i-2$  & |[state]| $i,W_i-1$ \\
      |[point]| & |[state]| $i+1,0$ & |[state]| $i+1,1$  & $\ldots$  & |[state]| $i+1,W_{i+1}-2$  & |[state]| $i+1,W_{i+1}-1$ \\
      [-1cm]
      |[point]| & |[stateinv]| \vdots & |[stateinv]| \vdots & |[stateinv]| \vdots & |[stateinv]| \vdots & |[stateinv]| \vdots \\
      |[point]| & |[state]| $m,0$ & |[state]| $m,1$  & $\ldots$  & |[state]| $m,W_m-2$  & |[state]| $m,W_m-1$ \\};
  \node[draw=none] (P1)[right of=m-3-3,,yshift=0.5cm]  {$\dfrac{p}{W_1}$};
  \node[draw=none] (P2)[right of=m-5-3,,yshift=0.5cm,xshift=1cm] {$\dfrac{p}{W_{i+1}}$};
  \node[draw=none] (P3)[right of=m-7-3,,yshift=0.5cm,xshift=1cm] {$\dfrac{p}{W_m}$};
  { [start chain] \chainin (m-1-1);
     \chainin (m-1-2);
    { [start branch=A] \chainin (m-2-2);}
    { [start branch=A] \chainin (m-2-3);}
    { [start branch=A] \chainin (m-2-5);}
    \chainin (m-2-6);}
  { [start chain] \chainin (m-2-6);
    \chainin (m-2-5) [join={node[above,labeled] {1}}];
    \chainin (m-2-4) [join={node[above,labeled] {1}}];
    \chainin (m-2-3) [join={node[above,labeled] {1}}];
    \chainin (m-2-2) [join={node[above,labeled] {1}}]; 
    \chainin (m-2-1) [join={node[above,labeled] {1-p}}]; }
  { [start chain] \chainin (m-2-2);
    { [start branch=A] \chainin (m-3-2);}
    { [start branch=A] \chainin (m-3-3);}
    { [start branch=A] \chainin (m-3-5);}
    \chainin (m-3-6);}
  { [start chain] \chainin (m-4-6);
    \chainin (m-4-5) [join={node[above,labeled] {1}}];
    \chainin (m-4-4) [join={node[above,labeled] {1}}];
    \chainin (m-4-3) [join={node[above,labeled] {1}}];
    \chainin (m-4-2) [join={node[above,labeled] {1}}];
    \chainin (m-4-1) [join={node[above,labeled] {1-p}}]; }
  { [start chain] \chainin (m-4-2);
    { [start branch=A] \chainin (m-5-2);}
    { [start branch=A] \chainin (m-5-3);}
    { [start branch=A] \chainin (m-5-5);}
    \chainin (m-5-6);}
  { [start chain] \chainin (m-5-6);
    \chainin (m-5-5) [join={node[above,labeled] {1}}];
    \chainin (m-5-4) [join={node[above,labeled] {1}}];
    \chainin (m-5-3) [join={node[above,labeled] {1}}];
    \chainin (m-5-2) [join={node[above,labeled] {1}}];
    \chainin (m-5-1) [join={node[above,labeled] {1-p}}]; }
   { [start chain] \chainin (m-6-2);
    { [start branch=A] \chainin (m-7-2);}
    { [start branch=A] \chainin (m-7-3);}
    { [start branch=A] \chainin (m-7-5);}
    \chainin (m-7-6);}
  { [start chain] \chainin (m-7-6);
    \chainin (m-7-5) [join={node[above,labeled] {1}}];
    \chainin (m-7-4) [join={node[above,labeled] {1}}];
    \chainin (m-7-3) [join={node[above,labeled] {1}}];
    \chainin (m-7-2) [join={node[above,labeled] {1}}];
    \chainin (m-7-1) [join={node[above,labeled] {1-p}}]; }
  { [start chain] \chainin (m-7-1);
    \chainin (m-1-1) [join={node[above,labeled] {1}}]; }
\end{tikzpicture}

The end result is the following: End result

As you can see, the lines from one row to the next start from everywhere and also end everywhere. What I would like to achieve is the following:

  • The start should always be at the bottom middle of the node so that it looks like the first row. Although that is a bit cheated as it originates in a point. But the style should be the same.
  • The end of the line should always be at the top middle of the node.

I guess one can use anchors to some extend as I have seen that done with paths, but I'm not sure how that works with chains. As I'm fairly new with TikZ, I would appreciate any explanation.

If there are any other comments to improve any other part, it is greatly appreciated!

Thank you in advance!

4

I don't see any good way to do that with the chains library, which seems to have trouble with node anchors. On the other hand, you don't seem to be making much use of the library beyond what is already easy to do using \draw[->].

Furthermore, while your application has lots of nodes and edges, many of them can be specified algorithmically. This is a good candidate for using the \foreach command!

\documentclass[tikz, border=3pt]{standalone}
\usepackage{tikz}
\usetikzlibrary{matrix, shapes, arrows}
\makeatletter
\DeclareRobustCommand{\rvdots}{%
  \vbox{
    \baselineskip4\p@\lineskiplimit\z@
    \kern-\p@
    \hbox{.}\hbox{.}\hbox{.}
  }}
\makeatother

\begin{document}
\begin{tikzpicture}
  \tikzset{>=stealth'}
  \tikzstyle{state}=[ellipse, draw]
  \tikzstyle{stateinv}=[inner sep=5pt]
  \tikzstyle{point}=[coordinate]
  \matrix (m) [matrix of nodes, row sep=4em, column sep=3em, nodes={anchor=center}]
    { |[point]| & |[point]| \\
      |[point]| & |[state]| $0,0$ & |[state]| $0,1$  & $\ldots$  & |[state]| $0,W_0-2$  & |[state]| $0,W_0-1$ \\
      |[point]| & |[stateinv]| \rvdots & |[stateinv]| \rvdots & |[stateinv]| \rvdots & |[stateinv]| \rvdots & |[stateinv]| \rvdots \\
      [-1cm]
      |[point]| & |[state]| $i,0$ & |[state]| $i,1$  & $\ldots$  & |[state]| $i,W_i-2$  & |[state]| $i,W_i-1$ \\
      |[point]| & |[state]| $i+1,0$ & |[state]| $i+1,1$  & $\ldots$  & |[state]| $i+1,W_{i+1}-2$  & |[state]| $i+1,W_{i+1}-1$ \\
      [-1cm]
      |[point]| & |[stateinv]| \rvdots & |[stateinv]| \rvdots & |[stateinv]| \rvdots & |[stateinv]| \rvdots & |[stateinv]| \rvdots \\
      |[point]| & |[state]| $m,0$ & |[state]| $m,1$  & $\ldots$  & |[state]| $m,W_m-2$  & |[state]| $m,W_m-1$ \\};

  \foreach \i [evaluate=\i as \ii using int(\i+1)] in {1,2,4,6}{
    \foreach \j in {2,3,6}{
      \draw[->] (m-\i-2.south) to (m-\ii-\j.north);
    }
  }
  \draw[->] (m-1-2) -- (m-2-5.north);
  \foreach \i/\label [evaluate=\i as \ii using int(\i+1)] in {2/i,4/i+1,6/m}{
    \draw[->] (m-\i-2.south) to node[below] {$\frac{p}{W_{\label}}$} (m-\ii-5.north);
  }
  \foreach \i in {2,4,5,7}{
    \foreach \j [remember=\j as \jj (initially 6)] in {5,...,2}{
      \draw[->] (m-\i-\jj) -- node[above] {\scriptsize$1$} (m-\i-\j);
    }
    \draw[->] (m-\i-2) -- node[above] {\scriptsize$p-1$} (m-\i-1);
  }
  \draw[->] (m-7-1) -- (m-1-1);
  \draw[->] (m-1-1) -- (m-1-2);
\end{tikzpicture}
\end{document}

Markov chain

(Credit to this answer for the \rvdots command with the same spacing above and below.)

You might also be interested in drawing curved edges like

\draw[->, out=180, in=90] (m-7-2) to node[left, pos=.2] {\scriptsize$p-1$} (m-2-2);
| improve this answer | |
  • This looks great! After a bit of testing, I also understand the syntax mostly. The command for the dots is a nice touch. I will probably not need the curved edges, but it's good to know the command! – Patrick Oct 19 '16 at 7:35

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.