How to make the matplotlib subscript and special characters? - python

I want to make a subscript for the axis label of my plot plotted using matplotlib. I have the following script snapshot:
import matplotlib.pylab as plt
plt.ylabel(r'$A^{2}$')
I have 2 questions:
In the plot, the subscript "2" seems occupying a whole word length in stead of half, which make the plot a little bit weird. How to make the subscript smaller (both in size and the length span)?
How to display "angstroms" (the length unit of 10^-10m) instead of A?
Thanks!

What version of matplotlib are you using? In my version the superscript seems fine (to me).
Im using python 2.6.5 and matplotlib 1.1.0
Use \AA for angstram --> plt.ylabel("$\AA$").
The circle is a bit small, though.

If it's available to you, try using TeX to render your text.
from matplotlib import rc
rc('text', usetex=True)
#the rest of your plotting code here
This should make your fonts and text look a whole lot better.
For more details on matplotlib's TeX rendering capabilities, look here: http://matplotlib.sourceforge.net/users/usetex.html

Related

matplotlib legend performance issue

I am using Jupyter-notebook with python 3.6.2 and matplotlib to plot some data.
When I plot my data, I want to add a legend to the plot (basically to know which line is which)
However calling plt.legend takes a lot of time (almost as much as the plot itself, which to my understanding should just be instant).
Minimal toy problem that reproduces the issue:
import numpy as np
import matplotlib.pyplot as plt
# Toy useless data (one milion x 4)
my_data = np.random.rand(1000000,4)
plt.plot(my_data)
#plt.legend(['A','C','G','T'])
plt.show()
The data here is just random and useless, but it reproduces my problem:
If I uncomment the plt.legend line, the run takes almost double the time
Why? Shouldn't the legend just look at the plot, see that 4 plots have been made, and draw a box assigning each color to the corresponding string?
Why is a simple legend taking so much time?
Am I missing something?
Replicating the answer by #bnaecker, such that this question is answered:
By default, the legend will be placed in the "best" location, which requires computing how many points from each line are inside a potential legend box. If there are many points, this can take a while. Drawing is much faster when specifying a location other than "best", e.g. plt.legend(loc=3).

SVG rendering issues using iPython inline plots

when I use inline plots in iPython (QtConsole), the first plot looks (more or less) fine, but then it gets weirder and weirder. When I plot something several times (so plot, see it displayed, plot again, see output etc.), it looks like it is being overlaid with the skewed previous picture. So after plotting a diagonal line (x=y) 4 times in a row I get something like this
If i right click and export it as svg everything looks good
(Exported PNG picture remains wrecked as the first one).
I guess the problem is similar to https://github.com/ipython/ipython/issues/1866, but I didn't got the upshot of the discussion (it got too technical and complicated for me to follow).
Is there any solution or work around for this issue?
I'm using
python 2.7
matplotlib 1.4.1
IPython 2.1.0
Here is a working example:
%matplotlib inline
% config InlineBackend.figure_format = 'svg'
import matplotlib.pyplot as plt
a=range(10)
fig,ax=plt.subplots()
ax.plot(a,a)
ax.axis('off')
if you remove plt.axis('off') line, weird things happen only outside of the axis box.
P.S. Originally I encountered this problem in connection with drawing graphs with networkx. If I use draw from networkx this problem does not occur. If I use draw_networkx, same as described above happens. That might point to the core of the problem... I'm trying to figure out what line of code makes one work better than the other...
After tinkering around with the draw and draw_networkx functions from networkx module, I found the workaround which makes the difference between draw and draw_networkx in this case.
Adding fig.set_facecolor('w') overlays whatever is in the background, so the new plots are started with a white sheet (but not a blank one, I guess).
So new working example is:
%matplotlib inline
% config InlineBackend.figure_format = 'svg'
import matplotlib.pyplot as plt
a=range(10)
fig,ax=plt.subplots()
fig.set_facecolor('w')
ax.plot(a,a)
ax.axis('off')

writing greek letters with subscripts with matplotlib

I have to use greek letter with subscript as axes label, so i thought to use Latex symbols. I am using the following code:
from matplotlib import rc
rc('font',**{'family':'sans-serif','sans-serif':['Helvetica']})
rc('text', usetex=True)
and in the plot I have, for example:
ylabel(r'$\boldsymbol{\delta_y}$')
It works fine, it is just slow (it take about 5 sec. to make a plot), I guess it is bacause python has to call an external package.
Any chances I can make it faster?
I am using python 2.6
Try using rc('text', usetex=False).
With this matplotlib will use the internal mathtext instead of your OS's latex installation to render math symbols. See the docs.

Python- Connecting Lines with plot_date in Matplotlib

I am using matplotlib to graph out some data in which takes time over a time, therefore I have to use plot_date in order to plot my lines. But for some reason Plot_Date and Plot have completely different formatting as far as connecting lines.
Here is what It looks like when using plot(x,y)
Using plot(x,y,'bo') or plot_date(x,y,'bo')
Plot_date(x,y) looks like that ^^ too.
and using plot_date(x,y,'bo-')
How do I make it so that the result of plot_date looks like the first picture? I have looked all over the Matplotlib website and couldn't find anything.
Thanks in advance
Upon further investigation I found that in order to display a solid line without dots, I needed to use the line style 'b-', making the code plot_date(x,y,'b-').
If you want to have the markers connected with the lines, you can also use
plt.plot_date(y,x,linestyle='solid')
So the complete code for the beginners would be:
from matplotlib import pyplot as plt
plt.plot_date(y,x,linestyle='solid')
plt.show()
Do not forget you need to have matplotlib installed first. For that you need to open command line and write:
pip install matplotlib

How to remove space only at the top of the plot - matplotlib

I've seen many posts and answers online trying to answer this question.
However using bbox_inches = 'tight' the legend disappears.
This is one of my figures:
Since I have the legend outside the plot frame, I would like to remove only the top and bottom white space.
Anyone knows how to remove at least the top white space?
Thanks a lot!
Have you tried using subplots_adjust()? See, for example, the answer of #DaveP to this question: Reduce left and right margins in matplotlib plot
Also, look at the answer by #Tian Chu to the same question.
EDIT: This works for me:
import matplotlib.pyplot as plt
fig=plt.figure()
ax=fig.add_subplot(111)
ax.plot([1,2,3],[5,6,7],'gs-')
plt.subplots_adjust(top=0.99, right=0.99)
plt.show()
I usually don't use the bbox_inches = 'tight' feature, since it doesn't work very reliably, as you already found out. I'd rather produce a PDF with bounds and then crop them using external tools. To do this seamless from python, I use
os.system('pdfcrop %s %s &> /dev/null &'%(pdf_in, pdf_out))
Here, pdf_in is the PDF you produced from matplotlib and pdf_out will be your final result.

Categories