Matplotlib is a plotting library. It relies on some backend to actually render
the plots. The default backend is the agg
backend. This backend only renders
PNGs. On Jupyter notebooks the matplotlib backends are special as they are
rendered to the browser. Generally you will not need to explicitly set the
backend on a Jupyter notebook. This does introduce a discrepancy between code
that runs in Jupyter and code that runs as a script natively in the Python
interpreter. So you need to understand that the 2 environments are not the same
and code that was written in Jupyter may not easily run inside the native Python
interpreter.
To get backends that are interactive or integrate into your operating system GUI, you need to know what OS you're running and what kind of backends have been compiled into your matplotlib library. Different backends have different compatibility requirements, and some backends only work on Python 2 instead of Python 3.
There's no easy way to find out what backends are available to be used, instead you can only really find out either by trial and error, or if you have access to the compilation logs. (If you compiled it yourself, you should know).
However you can find out what backend the matplotlib library is currently set to and you can find out the string keys that point to different backends.
This will show you what the default backend of matplotlib has been set to. If
you don't have any confounding environment variables nor a matplotlibrc
file,
then this should give back the string agg
.
import matplotlib.pyplot as plt
print(plt.get_backend())
You can find out the current matplotlibrc
file by doing:
import matplotlib as mpl
print(mpl.matplotlib_fname())
If you don't have a matplotlibrc
file, it will show the default sample file.
The list of backend string keys can be acquired with:
import matplotlib.rcsetup as rcsetup
print(rcsetup.interactive_bk)
print(rcsetup.non_interactive_bk)
print(rcsetup.all_backends)
Once you know which backend you want to use. In my case, I have the Qt4Agg
compiled into my matplotlib. (it was provided via matplotlib.override { enableQt = true; }
in shell.nix). I can then try to switch to it. These are the ways to do this:
The first is to use it just before importing pyplot
.
import matplotlib as mpl
mpl.use('Qt4Agg')
import matplotlib.pyplot as plt
plt.plot(range(20), range(20))
plt.show()
The second is to use an experimental function that allows you to switch backends, however this only works when switching from non-interactive to interactive and vice versa, not between interactive backends.
import matplotlib.pyplot as plt
plt.switch_backend('Qt4Agg')
plt.plot(range(20), range(20))
plt.show()
The third way to do this is to create a matplotlibrc
file which contains:
backend: Qt4Agg
However this is not preferred, as it's better to be explicit in the code that uses the matplotlib library, and multiple projects may need to use different backends.
The fourth and best way is to use an environment variable:
MPLBACKEND=Qt4Agg python -c 'import matplotlib.pyplot as plt; print(plt.get_backend())'
This is because you may be working on multiple computers on the same codebase,
then these computers may all support different backends. It is up to executor
to tell matplotlib what backend use. You can easily script this into your
development environment. When doing it this way, it is perfectly fine to use
plt.switch_backend
for switching to non-interactive backends to render plots
onto disk. The only backend you're guaranteed to have is agg
. You'll have to
test any other backends.
If you are stuck on the agg
backend, you cannot use plt.show()
, however you
can use plt.savefig
:
import matplotlib.pyplot as plt
plt.plot(range(20), range(20))
plt.savefig('linear.png')
Remember the behaviour of not having the right backend is undefined. Sometimes it is a silent failure, other times you'll get something else break.
When I use
matplotlib.use('Qt5Agg')
from matplotlib import pyplot as plt
THE CODE BODY
plt.show()
I always get the error
C:/Users/user/models/research/object_detection/object_detection_tutorial.py:162: UserWarning: Matplotlib is currently using agg, which is a non-GUI backend, so cannot show the figure.
It seems I got stuck on the agg backend. As you pointed,
plt.savefig
works.However I still want to find a way to make
plt.show()
work and ready to get your suggestion.