2

I have a graph that must show the oscillations in energy of a numerical scheme. The problem is that the energy is something like this:

-9.99999994950000e-01

and I have oscillations after 8 digits. At the moment, the graph is a straight line, so I can't see the oscillations.

How many digit pgfplots can use? Is there any way to see these oscillations?

  • The default unit of measure in PGF is 1cm. So a difference in the 8th decimal digit corresponds to tenth of nanometers, which can't be appreciated by the naked eye. You have to scale up everything at least ten million times to bring the differences in the range of millimeters. – egreg Nov 02 '12 at 10:25
  • @egreg Why pgfplots don't scale it automatically with scientific notation on axes? Pgfplots can process a 15-digit number or it consider only the first x digits (in this case the first eight because we see a straight line at -9.9999999e-1). –  Nov 02 '12 at 10:30
  • I don't know whether pgfplots can automatically scale; however this will require scaling at least ten million times, which would make for a huge graph. You should graph the differences, not the actual values. – egreg Nov 02 '12 at 10:33
  • Why a huge graph? With Matlab I can see the oscillations zooming a lot of times... –  Nov 02 '12 at 10:36
  • Probably Matlab is graphing the differences, not the actual values. – egreg Nov 02 '12 at 10:39
  • 1
    There is a section in the TikZ manual about the precision and significant digits. Pgfplots certainly inherits a few limitations from the underlying TeX engine. For the plot expression function a relative precision of 10^-4 to 10^-6 is stated, but I did not find a statement about other plot types. It would be easiest to just add +10 (and maybe rescale) your data, so that pgfplots does not need so many digits of precision. – Alexander Nov 02 '12 at 10:43
  • Not exactly the same, but a related question: http://tex.stackexchange.com/questions/70774/is-there-a-workaround-against-loss-of-precision-in-pgfplots-axis – alfC Nov 02 '12 at 15:28

1 Answers1

8

The problem here is that you want to display a data range of, say, -9.99999994950000e-01 to -9.99999995000000e-01 . The relative precision which is required to provide meaningful results here is beyond the capabilities of pgfplots, sorry.

However, you can assist it - if you have a math tool at hand. A "math tool" can be LuaLaTeX ... suppose you had LuaLaTeX, then the following might be a solution:

\documentclass{standalone}

\usepackage{pgfplots}

\begin{document}

\begin{tikzpicture}
\def\SHIFT{-0.99999999}
\def\EXPONENT{9}%
    \begin{axis}[
        y coord trafo/.code={%
            \edef\pgfmathresult{\directlua{tex.print( (#1 - (\SHIFT))*10^(\EXPONENT) )}}%
            \message{#1 -> \pgfmathresult^^J}%
        },
        y coord inv trafo/.code={%
            \edef\pgfmathresult{\directlua{tex.print( #1*10^(-\EXPONENT) + (\SHIFT) )}}%
            \message{inv: #1 -> \pgfmathresult^^J}%
        },
        yticklabel style={
            /pgf/number format/precision=11,
            /pgf/number format/fixed zerofill,
        },
    ]
    \addplot table {
    0 -9.99999994950000e-01
    1 -9.99999995000000e-01
    2 -9.99999995010000e-01
    };
    \end{axis}
\end{tikzpicture}
\end{document}

enter image description here

It employs Lua's math capabilities in order to transform your input data into some range where pgfplots can apply its arithmetics. Later, it uses Lua again to transform the intermediate results back. The number printer is lossless (as it operates on symbols only).

Note that this affine transformation consisting of shifts and an exponent is very similar to what pgfplots does internally. It just can't cope with such high relative precisions.

If you do not have LuaLaTeX, you can still try to prepare your data. Apparently, the energy is being computed by some numeric algorithm. If you would apply such a transformation manually, you could display it. You would need to get meaningful tick labels, which is less elegant than my first approach, but still feasible (for example by providing them manually).

Henri Menke
  • 109,596
  • 1
    Without lua one could use expl3's fp module using something like \cs_new_eq:NN \mathexpr \fp_eval:n. (I just tested it on the example...) – cgnieder Nov 02 '12 at 21:05
  • @cgnieder I was wondering if that might work: presumably any IEEE854-compliant implementation is suitable, although I'd strongly suggest some pre-processing in a proper tool. – Joseph Wright Nov 02 '12 at 21:11