如何在 pgfplots 中绘制函数总和

如何在 pgfplots 中绘制函数总和

我想绘制脉冲总和,以描绘通过引入 ISI 的通信信道传输的二进制脉冲。我可以通过围绕 \addplot 命令放置一个 \foreach 循环来绘制单个脉冲,为每个脉冲添加一个图,如以下代码所示:

\documentclass{beamer}
\usepackage{tikz}


\usetikzlibrary{positioning,arrows,shapes.arrows,shapes.geometric,calc,decorations.markings,patterns}
\usepackage{ifthen}
\usepackage{pgfplots}
\setbeamertemplate{navigation symbols}{}

%%%%%%%%%%%%%%%%%%%%
% Draw the user bits 
\newcommand{\userBits}[3]{
  % #1 the location west anchor of the bit array
  % #2 a base label identifying this set of bits, eg: userBits or parityBits
  % #3 the contents of the foreach loop that creates the bit array eg: a/1/0,b/1/1,c/0/2
  % The first component is part of the label for the node box created that holds the bit
  % The second component is the contents of the box that is written onto the page
  % The third component is needed for compatibility with the drawIndividualWaveforms function
  %                     it is not used in this function, but should still be there for compatibility.
  \coordinate(O) at ($#1$);
  \foreach\i/\j/\k in {#3}{
    \node [bitBox,fill=blue!15] at (O)(#2\i){\j};
    \coordinate(O) at (#2\i.0);
  }
}


\newcommand{\drawIndividualWaveforms}[3]{
  % #1 the location of the plot of individual waveforms
  % #2 a label for this node
  % #3 the contents of the for loop holding 3 components such as a/+/0:
  %    first component is a sublabel for this particular bit
  %    second component is the value of the bit either + or -
  %    third component is a k index indicating the delay of this wave pulse.
  \node at ($#1$){\tikz{
  \begin{axis} [axis lines =left,
      width=6cm, height=2.7cm,
      xtick=\empty,xticklabel=\empty,
      ytick=\empty,yticklabel=\empty,
      axis x line = middle,
      ymin=-1.1, ymax=1.1,
      xmin=0, xmax=7,
    ]
    \foreach\i/\j/\k in{#3}{
      \ifthenelse{\equal{\j}{+}}{
        \addplot[domain=\k-1:\k+1,
          samples=21,] {exp(-(x-\k)*(x-\k)*4)}; %{0.5*cos(180*x-180*\k)+0.5};
      }{
        \addplot[domain=\k-1:\k+1,
          samples=21,] {-exp(-(x-\k)*(x-\k)*4)}; %{-0.5*cos(180*x-180*\k)-0.5};
      }
    }
  \end{axis}      
  }};
}
\newcommand{\drawCombinedWaveforms}[3]{
  % #1 the location of the plot of individual waveforms
  % #2 a label for this node
  % #3 the contents of the for loop holding 3 components such as a/+/0:
  %    first component is a sublabel for this particular bit
  %    second component is the value of the bit either + or -
  %    third component is a k index indicating the delay of this wave pulse.
  \node at ($#1$){\tikz{
  \begin{axis} [axis lines =left,
      width=6cm, height=2.7cm,
      xtick=\empty,xticklabel=\empty,
      ytick=\empty,yticklabel=\empty,
      axis x line = middle,
      ymin=-1.1, ymax=1.1,
      xmin=0, xmax=7,
    ]
    \def\k{5}
    \addplot[domain=0:7,samples=101]{
      \foreach\i/\j\k in {#3}{
        +exp(-(x-\k)*(x-\k)*4)
      }
    };
  \end{axis}      
  }};
}
\pgfplotsset{compat=1.9}
\tikzset{>=stealth,
  signalLabel/.style={text centered,font=\scriptsize,above,align=center},
  boundingBox/.style={use as bounding box},
  channelModule/.style={scale=.7,draw,top color=blue!30,align=center,inner sep=0.25cm,minimum height=1.2cm,node distance=0.75cm,minimum width=1.5cm},
  bitBox/.style={anchor=180,draw,font=\scriptsize,inner sep=0,minimum width=0.33cm,minimum height=0.4cm}
}
%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% Begin document           %
%%%%%%%%%%%%%%%%%%%%%%%%%%%%
\begin{document}
\newcommand{\channelSubFrame}[2]{
  % Create a subframe for the animation demonstrating the parity check ENCODING process
  % #1 Flag for the contenst of the channel box. 0: Channel. 1: Raised cosine pulse 2: raised cosine pulse AND draw the summation of the pulses rather than individual pulses
  % #2 channel bits as input to the channel
\begin{frame}{Intersymbol Interference (ISI) Channel}
  \begin{tikzpicture}
    \path[boundingBox](0,0) rectangle ++(11,6);     % Set the BB
    \ifthenelse{\equal{#1}{0}}{
      \node[channelModule,scale=1.4] at (4.5,5)(channel){Channel};
    }{
      \node[channelModule,inner sep=0.3cm] at (4.5,5)(channel){ISI Channel};
    }
    \draw[<-](channel.180)--node[above,signalLabel]{Channel bits $\mathbf{c}_k$}++(-4,0);
    \draw[->](channel.0)--node[above,signalLabel]{Readback waveform $\mathbf{r}_k$}++(5,0);
    \ifthenelse{\equal{#2}{}}{}{ % Only try to draw the user bits and waveforms if a set of bits (#2) has been provided by the caller
      \userBits{(channel.south west)+(-3.0,0.0)}{channelBit}{#2} % Draw the user bits at the channel input
      \ifthenelse{\equal{#1}{1}}{ % if equal to 1, then draw the separated pulses
        \drawIndividualWaveforms{(channel.south east)+(2.5,-0.25)}{channelWaveform}{#2} % Draw the waveform consisting of the individual components of the impulse response
      }{                          % if equal to 2 then draw the combined waveform.
        \drawCombinedWaveforms{(channel.south east)+(2.5,-0.25)}{channelWaveform}{#2} % Draw the waveform consisting of the summation of the components of the impulse response
      }
    }
  \end{tikzpicture}
\end{frame}}
\channelSubFrame{1}{}
\channelSubFrame{1}{a/+/1}
\channelSubFrame{1}{a/+/1,b/--/2}
\channelSubFrame{1}{a/+/1,b/--/2,c/--/3}
\channelSubFrame{1}{a/+/1,b/--/2,c/--/3,d/+/4}
\channelSubFrame{1}{a/+/1,b/--/2,c/--/3,d/+/4,e/--/5}
\channelSubFrame{1}{a/+/1,b/--/2,c/--/3,d/+/4,e/--/5,f/+/6}
\end{document}

我可以在同一张图上绘制多个脉冲,但无法将这些脉冲的总和绘制成单个波形。我尝试将 \foreach 循环放在 \addplot 中,如我尝试定义的 \drawCombinedWaveforms 命令中所示,但没有成功。任何帮助都非常感谢!谢谢

答案1

这是累积函数的一种方法。注意应该不是nest tikzpicures,完全没有必要,您可以使用 键shift移动轴。除此之外,还有几件事可以更改,例如 pgfplots 兼容版本。

\documentclass{beamer}
\usepackage{ifthen}
\usepackage{pgfplots}
\usetikzlibrary{positioning,arrows,shapes.arrows,shapes.geometric,calc,decorations.markings,patterns}
\setbeamertemplate{navigation symbols}{}

%%%%%%%%%%%%%%%%%%%%
% Draw the user bits 
\newcommand{\userBits}[3]{
  % #1 the location west anchor of the bit array
  % #2 a base label identifying this set of bits, eg: userBits or parityBits
  % #3 the contents of the foreach loop that creates the bit array eg: a/1/0,b/1/1,c/0/2
  % The first component is part of the label for the node box created that holds the bit
  % The second component is the contents of the box that is written onto the page
  % The third component is needed for compatibility with the drawIndividualWaveforms function
  %                     it is not used in this function, but should still be there for compatibility.
  \coordinate(O) at ($#1$);
  \foreach\i/\j/\k in {#3}{
    \node [bitBox,fill=blue!15] at (O)(#2\i){\j};
    \coordinate(O) at (#2\i.0);
  }
}


\newcommand{\drawIndividualWaveforms}[3]{
  % #1 the location of the plot of individual waveforms
  % #2 a label for this node
  % #3 the contents of the for loop holding 3 components such as a/+/0:
  %    first component is a sublabel for this particular bit
  %    second component is the value of the bit either + or -
  %    third component is a k index indicating the delay of this wave pulse.
  \begin{axis} [shift={($#1+(0,-1cm)$)},axis lines =left,
      width=6cm, height=2.7cm,
      xtick=\empty,xticklabel=\empty,
      ytick=\empty,yticklabel=\empty,
      axis x line = middle,
      ymin=-1.1, ymax=1.1,
      xmin=0, xmax=7,
    ]
    \foreach\i/\j/\k in{#3}{
      \ifthenelse{\equal{\j}{+}}{
        \addplot[domain=\k-1:\k+1,
          samples=21,] {exp(-(x-\k)*(x-\k)*4)}; %{0.5*cos(180*x-180*\k)+0.5};
      }{
        \addplot[domain=\k-1:\k+1,
          samples=21,] {-exp(-(x-\k)*(x-\k)*4)}; %{-0.5*cos(180*x-180*\k)-0.5};
      }
    }
  \end{axis}      
  }
\newcommand{\drawCombinedWaveforms}[3]{
  % #1 the location of the plot of individual waveforms
  % #2 a label for this node
  % #3 the contents of the for loop holding 3 components such as a/+/0:
  %    first component is a sublabel for this particular bit
  %    second component is the value of the bit either + or -
  %    third component is a k index indicating the delay of this wave pulse.
  \begin{axis} [shift={($#1+(0,-1cm)$)},axis lines =left,
      width=6cm, height=2.7cm,
      xtick=\empty,xticklabel=\empty,
      ytick=\empty,yticklabel=\empty,
      axis x line = middle,
      ymin=-1.1, ymax=1.1,
      xmin=0, xmax=7,
    ]
    \def\k{5}
    \def\myf{0}
    \foreach\i/\j/\k in {#3}{
        \ifthenelse{\equal{\j}{+}}{
        \xdef\myf{\myf+exp(-(x-\k)*(x-\k)*4)}
        }{
        \xdef\myf{\myf-exp(-(x-\k)*(x-\k)*4)}
        }
      }
    \addplot[domain=0:7,samples=101,color=blue]{\myf};
  \end{axis}      
  }
\pgfplotsset{compat=1.9}
\tikzset{>=stealth,
  signalLabel/.style={text centered,font=\scriptsize,above,align=center},
  boundingBox/.style={use as bounding box},
  channelModule/.style={scale=.7,draw,top color=blue!30,align=center,inner sep=0.25cm,minimum height=1.2cm,node distance=0.75cm,minimum width=1.5cm},
  bitBox/.style={anchor=180,draw,font=\scriptsize,inner sep=0,minimum width=0.33cm,minimum height=0.4cm}
}
%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% Begin document           %
%%%%%%%%%%%%%%%%%%%%%%%%%%%%
\begin{document}
\newcommand{\channelSubFrame}[2]{
  % Create a subframe for the animation demonstrating the parity check ENCODING process
  % #1 Flag for the contenst of the channel box. 0: Channel. 1: Raised cosine pulse 2: raised cosine pulse AND draw the summation of the pulses rather than individual pulses
  % #2 channel bits as input to the channel
\begin{frame}{Intersymbol Interference (ISI) Channel}
  \begin{tikzpicture}
    \path[boundingBox](0,0) rectangle ++(11,6);     % Set the BB
    \ifthenelse{\equal{#1}{0}}{
      \node[channelModule,scale=1.4] at (4.5,5)(channel){Channel};
    }{
      \node[channelModule,inner ysep=0.7cm,inner xsep=0.3cm] at (4.5,5)(channel){ISI Channel};
    }
    \draw[<-](channel.180)--node[above,signalLabel]{Channel bits $\mathbf{c}_k$}++(-4,0);
    \draw[->](channel.0)--node[above,signalLabel]{Readback waveform $\mathbf{r}_k$}++(5,0);
    \ifthenelse{\equal{#2}{}}{}{ % Only try to draw the user bits and waveforms if a set of bits (#2) has been provided by the caller
      \userBits{(channel.south west)+(-3.0,0.0)}{channelBit}{#2} % Draw the user bits at the channel input
      \ifthenelse{\equal{#1}{1}}{ % if equal to 1, then draw the separated pulses
        \drawIndividualWaveforms{(channel.south east)+(2.5,-0.25)}{channelWaveform}{#2} % Draw the waveform consisting of the individual components of the impulse response
      }{                          % if equal to 2 then draw the combined waveform.
        \drawCombinedWaveforms{(channel.south east)+(2.5,-0.25)}{channelWaveform}{#2} % Draw the waveform consisting of the summation of the components of the impulse response
      }
    }
  \end{tikzpicture}
\end{frame}}
\channelSubFrame{1}{}
\channelSubFrame{1}{a/+/1}
\channelSubFrame{1}{a/+/1,b/--/2}
\channelSubFrame{0}{a/+/1,b/--/2}
\channelSubFrame{1}{a/+/1,b/--/2,c/--/3}
\channelSubFrame{0}{a/+/1,b/--/2,c/--/3}
\channelSubFrame{1}{a/+/1,b/--/2,c/--/3,d/+/4}
\channelSubFrame{0}{a/+/1,b/--/2,c/--/3,d/+/4}
\channelSubFrame{1}{a/+/1,b/--/2,c/--/3,d/+/4,e/--/5}
\channelSubFrame{0}{a/+/1,b/--/2,c/--/3,d/+/4,e/--/5}
\channelSubFrame{1}{a/+/1,b/--/2,c/--/3,d/+/4,e/--/5,f/+/6}
\channelSubFrame{0}{a/+/1,b/--/2,c/--/3,d/+/4,e/--/5,f/+/6}
\end{document}

在此处输入图片描述

相关内容