11

I'm new to TikZ plotting. :)

I want to plot data from a CSV with pgfplots in an axis environment. The data has a quite large range, for which a linear y-axis isn't very appropriate. In Python's matplotlib is a scaling called symlog (for symmetric log: A mirrored log scale around the x-axis), which also allows negative values (e.g., a range from -(10^5) to 10^5) Since ymode=symlog doesn't work, is there any other way to create symlog-like plots?

My code is equivalent to (works only for the positive values):

\begin{tikzpicture}
\begin{axis}[
    xmode=linear,
    ymode=log,
    xlabel=$f$ (Hz),
    ylabel=$T$ (-),
    title={Measured transfer function of analogue filter},
    grid=both,
    minor grid style={gray!25},
    major grid style={gray!25},
    width=0.75\linewidth,
    no marks]
\addplot[line width=1pt,solid,color=blue] %
    coordinates {(0,-1000) (1,-100) (2,-10) (3,-1) (4,0) (5,1) (6,10) (7,100) (8,1000)};
\addlegendentry{Transfer function};
\end{axis}
\end{tikzpicture}

Source: https://olivierpieters.be/blog/2015/10/23/latex-plotting-from-file.html

Edit:

The result is:

enter image description here

But for coordinates {(0,-1000) (1,-100) (2,-10) (3,-1) (4,0) (5,1) (6,10) (7,100) (8,1000)}; the plot should look like (the scaling between -1 and +1 is linear):

enter image description here

5
  • Welcome to TeX.SX! What should the resulting plot look like? Do you have an example image from Python?
    – strpeter
    Jan 16, 2017 at 16:53
  • Your pyplot example is wrong! The values after ..., -(10^1), -(10^0) should be -(10^-1), -(10^2).... Jan 19, 2017 at 5:55
  • 2
    No, that's what I want to achieve. I want to display large data ranges ( big negative numbers to +2), for which linear isn't appropriate, because it's beginning to get interesting around zero. Symlog stands for symmetric log. So it's a mirrored log scale around the x-axis
    – psyruhi
    Jan 20, 2017 at 9:08
  • 1
    This is not implemented out of the box by pgfplots. I think what you need is possible thanks to the y coord trafo feature detailed in the pgfplots manual, section 4.21 Symbolic Coordinates and User Transformations See also this answer, in a more simple situation (for x -> x^2 scaling).
    – marsupilam
    Jan 20, 2017 at 10:18
  • 1
    As marsupilam already stated that is not supported yet. In fact, there is already a feature request for that in the PGFPlots Tracker. Jan 20, 2017 at 10:34

1 Answer 1

13

Here we go, using the y coord trafo key from pgfplots.

The symlog function is defined using the tikzmath.

It is the function enter image description here

For some reason, I can't seem to be able to plot a tikzmath function including if conditionals with pgfplots, hence the clumsiness of the symlog internals.

We also define the inverse transform symexp and feed it to the y coord inv trafo key, to be able to use the axis coordinate system.

It is the function enter image description here

The code

producing the following output :

enter image description here

\documentclass[tikz]{standalone}
\usepackage{pgfplots}
\usetikzlibrary{math}
\tikzmath
{
  function symlog(\x,\a){
    \yLarge = ((\x>\a) - (\x<-\a)) * (ln(max(abs(\x/\a),1)) + 1);
    \ySmall = (\x >= -\a) * (\x <= \a) * \x / \a ;
    return \yLarge + \ySmall ;
  };
  function symexp(\y,\a){
    \xLarge = ((\y>1) - (\y<-1)) * \a * exp(abs(\y) - 1) ;
    \xSmall = (\y>=-1) * (\y<=1) * \a * \y ;
    return \xLarge + \xSmall ;
  };
}
\begin{document}
\begin{tikzpicture}
  \def\basis{1}
  \pgfplotsset
  {
    y coord trafo/.code={\pgfmathparse{symlog(#1,\basis)}\pgfmathresult},
    y coord inv trafo/.code={\pgfmathparse{symexp(#1,\basis)}\pgfmathresult},
    yticklabel style={/pgf/number format/.cd,int detect,precision=2},
}
  \begin{axis}
    [
      height=12cm,
      legend pos=north west,
      scaled ticks = base 10:0,
      domain = -5:5.5,
      ytick = {-100,-10, -1,0,1,10,100},
      minor ytick = {-90,-80,...,-20,-9,-8,...,-2,-.9,-.8,...,.9,2,3,...,9,20,30,...,90},
      tick label style = {fill=white, fill opacity=.7},
      yminorgrids = true,
      ymajorgrids = true,
      xmajorgrids = true,
      samples=200,
      axis lines=center,
    ]
    \addplot+ [mark=none] {x} ;
    \addplot+ [mark=none] {exp(x)} ;
    \addplot+ [mark=none] {-exp(-x)} ;
    \legend {$x$,$e^x$,$-e^{-x}$}
  \end{axis}
\end{tikzpicture}
\end{document}

Cheers,

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.