# Defining a Piecewise Function for PGFplots

I want to define a piecewise function q(x), and attempted to adapt the solution to this question on using pgfmathdeclarefunction to create a unit pulse function, and this works fine. However, when I attempt to plot q(x+4)+0.5, the resulting graph is not what I would expect. However, applying the same transformation on the unit pulse function from the above mentioned link works fine.

So, is there a better way to define a piecewise defined function?

The MWE below produces the following result. Note that the graphs on the left are as one would expect for both p(x) and p(x+4)+0.5. The graphs on the right are correct for q(x), but but incorrect for q(x+4)+0.5.

\documentclass{article}
\usepackage{amsmath}
\usepackage{pgfplots}

\newcommand{\pLabel}{
$p(x)= \begin{cases} 1 & 0 < x < 1\\ 0 & \text{otherwise} \end{cases}$
}
\newcommand{\qLabel}{
$q(x)= \begin{cases} x & 0 < x < 1\\ 0 & \text{otherwise} \end{cases}$
}

\newcommand{\pShiftedLabel}{$p(x+4)+0.5$}
\newcommand{\qShiftedLabel}{$q(x+4)+0.5$}

\pgfmathdeclarefunction{p}{1}{%
\pgfmathparse{(and(#1>0, #1<1))}%
}

\pgfmathdeclarefunction{q}{1}{%
\pgfmathparse{(and(#1>0, #1<1)*x)}%
}

\tikzstyle{MyStyle}=[domain=-5:5, samples=50, ultra thick]
\tikzstyle{pLabelStyle}=[above, yshift=22ex, xshift=-10ex]
\tikzstyle{qLabelStyle}=[below, yshift=-2ex, xshift=-10ex]
\tikzstyle{ShiftedLabelStyle}=[above left, xshift=1ex]

\begin{document}
%------------------ Using \pgfmathdeclarefunction -----------
Plot of $p(x)$ and \pShiftedLabel using PGF Version \pgfversion, followed by a plot of $q(x)$ and \qShiftedLabel

\begin{tikzpicture}
\begin{axis}
\end{axis}
\end{tikzpicture}
%
\begin{tikzpicture}
\begin{axis}
\end{axis}
\end{tikzpicture}

% --------------------- Using "declare function" -------------
Using declare function to define localp(x) and localq(x):

\begin{tikzpicture}
[declare function={localp(\t) =  and(\t > 0, \t < 1);}]
\begin{axis}
\end{axis}
\end{tikzpicture}
%
\begin{tikzpicture}
[declare function={localq(\t) = (and(\t > 0, \t < 1)*x);}]
\begin{axis}
\end{axis}
\end{tikzpicture}
\end{document}


Both methods for defining piecewise functions are fine, but you should use

\pgfmathdeclarefunction{q}{1}{%
\pgfmathparse{(and(#1>0, #1<1)*#1)}%
}


instead of and(#1>0, #1<1)*x), and

[declare function={localq(\t) = (and(\t > 0, \t < 1)*\t);}]


instead of [declare function={localq(\t) = (and(\t > 0, \t < 1)*x);}], because you don't actually want the function value to be x, but rather the value of the argument (x+4 in this case).

\documentclass{article}
\usepackage{amsmath}
\usepackage{pgfplots}

\newcommand{\pLabel}{
$p(x)= \begin{cases} 1 & 0 < x < 1\\ 0 & \text{otherwise} \end{cases}$
}
\newcommand{\qLabel}{
$q(x)= \begin{cases} x & 0 < x < 1\\ 0 & \text{otherwise} \end{cases}$
}

\newcommand{\pShiftedLabel}{$p(x+4)+0.5$}
\newcommand{\qShiftedLabel}{$q(x+4)+0.5$}

\pgfmathdeclarefunction{p}{1}{%
\pgfmathparse{(and(#1>0, #1<1))}%
}

\pgfmathdeclarefunction{q}{1}{%
\pgfmathparse{(and(#1>0, #1<1)*#1)}%
}

\tikzstyle{MyStyle}=[domain=-5:5, samples=100, ultra thick]
\tikzstyle{pLabelStyle}=[above, yshift=22ex, xshift=-10ex]
\tikzstyle{qLabelStyle}=[below, yshift=-2ex, xshift=-10ex]
\tikzstyle{ShiftedLabelStyle}=[above left, xshift=1ex]

\begin{document}
%------------------ Using \pgfmathdeclarefunction -----------
Plot of $p(x)$ and \pShiftedLabel using PGF Version \pgfversion, followed by a plot of $q(x)$ and \qShiftedLabel

\begin{tikzpicture}
\begin{axis}
\end{axis}
\end{tikzpicture}
%
\begin{tikzpicture}
\begin{axis}
\end{axis}
\end{tikzpicture}

% --------------------- Using "declare function" -------------
Using declare function to define localp(x) and localq(x):

\begin{tikzpicture}
[declare function={localp(\t) =  and(\t > 0, \t < 1);}]
\begin{axis}
\end{axis}
\end{tikzpicture}
%
\begin{tikzpicture}
[declare function={localq(\t) = (and(\t > 0, \t < 1)*\t);}]
\begin{axis} • Thanks, not sure if I ever would have realized my mistake. The problem came about as I had defined \newcommand{\PieceA}{x} and was using that in my original code (I eliminated that for the MWE). So I would have to use \pgfmathparse{(and(#1>0, #1<1)*\PieceA)}. Is there a simple way to change definition of \PieceA to get this to work. I tried the ##1 trick that is used when a newcommand is defined within newcommand, but that didn't work. – Peter Grill May 31 '11 at 8:27
• @Peter: Not that I know of. I tried \edef\PieceA{\noexpand#1}, but that doesn't work. This should probably go into a new question, I'm sure there are some TeX cracks who know what to do. – Jake May 31 '11 at 8:37
• @Peter I admit that I do not see the bigger picture - it appears as if you really need the macro expansion. Does it help if you make \PieceA dependent on the variable, i.e. \newcommands{\PieceA}{#1}? This would allow you to replace \PieceA by some expression like \newcommand{\PieceA}{(#1+4)} AND it would fix your problem because you could write ...#1<1)*\PieceA{#1})}. But its just guessing. – Christian Feuersänger Aug 1 '11 at 21:22