Error using LaTeX for plot rendering in MacOS 10.11 - python

I recently made a clean install of OSX 10.11, installed Anaconda with python 3.5, Xcode, MacTex 2015 and updated all of these.
I have a problem when I want to use LaTeX in matplotlib.
Here is a short example:
import numpy as np
import matplotlib.pyplot as plt
from matplotlib import rc
rc('font', **{'family': 'serif', 'serif': ['Computer Modern']})
rc('text', usetex=True)
b = np.array([10, 11, 12, 13],dtype=np.float)
bStd = np.array([1.4, 0.6, 0.3, 1.1],dtype=np.float)
N = len(b)
ind = np.arange(N,dtype=np.float)
width = 0.8
FS=11
fig, ax = plt.subplots(figsize=(5.9055, 3.937))
Test = ax.plot(ind,b)
yerr = plt.errorbar(ind,b,bStd)
ax.set_title('Lorem ipsum dolor sit amet...', fontsize = FS, family = ['serif'])
ax.set_xticks(ind)
ax.set_xlim([-width, N-1+width])
ax.set_xticklabels( ('A','B','C','D'), fontsize = FS, family = ['serif'])
ax.set_ylabel('Value / $X/yy^2$',multialignment="center",fontsize = FS, family = ['serif'])
ax.set_ylim(0,20)
plt.tight_layout()
plt.savefig('Test.pdf', format='pdf',bbox_inches='tight')
When I try to use TeX in matplotlib, I receive the following:
RuntimeError: LaTeX was not able to process the following string:
b'lp'
Here is the full report generated by LaTeX:
I think that Spyder does not know how to access LaTeX. May this be a problem of the new rootless feature in El Capitan?
I already searched the web and of course Stackoverflow, but none of the suggestions, I found there, helped me.
Do you have any idea?
I just started to learn how to work with python, therefore I am really inexperienced, which might be visible in my example.
Thank you for your time.

Using Spyder as installed with MacPorts, I have the very same problems, but using Python3 as installed by MacPorts on a Mac OS Terminal, everything compiles fine (which seems strange since Spyder relies on this version of Python...).
As a workaround, if using the Terminal is fine for you, you may run directly your script from the Terminal (however, make sure that you use python as installed by anaconda by giving the explicit path to the executable), but this defeats the purpose of installing a nice GUI such as Spyder.

Related

MatplotlibDeprecationWarning: Support for FigureCanvases without a required_interactive_framework attribute

I'm trying to use matplotlib and numpy to plot a graph but keep running into this error:
MatplotlibDeprecationWarning: Support for FigureCanvases without a required_interactive_framework attribute was deprecated in Matplotlib 3.6 and will be removed two minor releases later.
plt.plot(cache_sizes, hit_rates[i])
Any idea how to solve it?
Here's the code:
#!/usr/bin/env python3
import os
import subprocess
import matplotlib.pyplot as plt
import numpy as np
# cache_sizes = np.arange(0, 120, 20)
cache_sizes = np.arange(1, 5)
policies = ["FIFO", "LRU", "OPT", "UNOPT", "RAND", "CLOCK"]
# these were acheived after running `run.sh`
hit_rates = [
# FIFO
[45.03, 83.08, 93.53, 97.42],
# LRU
[45.03, 88.04, 95.20, 98.30],
# OPT
[45.03, 88.46, 96.35, 98.73],
# UNOPT
# NOTE: was unable to finish running this one, as it took too long.
[45.03, None, None, None],
# RAND
[45.03, 82.06, 93.16, 97.36],
# CLOCK
[45.03, 83.59, 94.09, 97.73],
]
for i in range(len(policies)):
plt.plot(cache_sizes, hit_rates[i])
plt.legend(policies)
plt.margins(0)
plt.xticks(cache_sizes, cache_sizes)
plt.xlabel("Cache Size (Blocks)")
plt.ylabel("Hit Rate")
plt.savefig("workload.png", dpi=227)
Best I can tell, this is related to the backend you're using and how it generates the FigureCanvas object. Matplotlib has introduced a deprecation and some other softwares are still in the process of being updated accordingly. Sadly, for now, it's generating a warning that is not very user friendly and the matplotlib documentation provides no help.
I was seeing this error in PyCharm, which by default uses its own internal backend for matplotlib: 'module://backend_interagg'. Google provides a bunch of examples of people getting errors to do with FigureCanvas and backend_interagg. Fortunately, updating to the newest version of PyCharm solved it for me.
If your problem is not PyCharm related, then perhaps try checking which backend you're using, and perhaps use a different one.
import matplotlib
matplotlib.get_backend()
will show you which backend you're using
matplotlib.use('')
will give you a list of available backends to try and then use will also allow you to select one. e.g. matplotlib.use('GTK3Agg')

Codes in Ipython vs Pycharm

I am a newbie and the following question may be dumb and not well written.
I tried the following block of codes in Ipython:
%pylab qt5
x = randn(100,100)
y = mean(x,0)
import seaborn
plot(y)
And it delivered a plot. Everything was fine.
However, when I copied and pasted those same lines of codes to Pycharm and tried running, syntax error messages appeared.
For instance,
%pylab was not recognized.
Then I tried to import numpy and matplotlib one by one. But then,
randn(.,.) was not recognized.
You can use IPython/Jupyter notebooks in PyCharm by following this guide:
https://www.jetbrains.com/help/pycharm/using-ipython-jupyter-notebook-with-pycharm.html
You may modify code like the snippet below in order to run in PyCharm:
from numpy.random import randn
from numpy import mean
import seaborn
x = randn(10, 10)
y = mean(x, 0)
seaborn.plt.plot(x)
seaborn.plt.show()

IPython notebook doubles up the qqplot

I just tested the statsmodels.api.qqplot function in an IPython notebook (Jupyter) running Python 3.6, and got two identical plots in a column (I only asked for one). What is going on?
import statsmodels.api as sm
test = np.random.normal(0,1, 1000)
sm.qqplot(test, line='45')
Just add ";" is the simplest hack.
For example:
sm.qqplot(test, line='45');
I got the answer from
#lightalchemist from github.com/statsmodels/statsmodels/issues/1265.

IPython InteractiveShell fails to yield rich output when using `%matplotlib inline`

I am writing a custom client (a web-based graph representation of an IPython Notebook) for an IPython application and the easiest way to manage IPython programmatically seems to be using the IPython.core.InteractiveShell instance.
Consider this example: when a Jupyter Notebook cell that uses rich output is executed with inline magic, Notebook shows the appropriate rich representation (a plotted image) of plt.show() inline:
%matplotlib inline
import matplotlib.pyplot as plt
import numpy as np
t = np.arange(0.0, 2.0, 0.01)
s = np.sin(2*np.pi*t)
plt.plot(t, s)
plt.xlabel('time (s)')
plt.ylabel('voltage (mV)')
plt.title('About as simple as it gets, folks')
plt.grid(True)
plt.show()
I want to be able to retrieve the image when using IPython programmatically via its API, namely InteractiveShell, like this:
from IPython.core.interactiveshell import InteractiveShell
shell = InteractiveShell()
result = shell.run_cell("...above code of the cell here...")
# result either gives an error when using %matplotlib inline or retrieves
# no useful info if no line magic is present
Problem is that InteractiveShell instance will not accept the %matplotlib inline magic, giving a NotImplementedError in its enable_gui method which is, wll, not implemented. I found very few information about this apart from a single issue on IPython's Github.
I know I can do this manually by using plt.save() but that doesn't seem right to me as I don't want to write manual interpretations each time I need another rich representation of the result. I feel like I'm missing a lot here in the way IPython works, so I'm asking for help in retrieving the results. What exactly does Jupyter Notebook do to retrieve the rich representation and perhaps can it be done painlessly via other means? I'm looking at using jupyter_client but for now that seems to be even more confusing.
UPDATE:
The io.capture_output context manager seems to be the way to go but I've been able to capture string outputs only (pretty much the same as using %%capture cell magic):
with io.capture_output() as captured:
result = shell.run_cell(cell)
#captures strings only:
captured.stdout = {str} '<matplotlib.figure.Figure at 0x4f486d8>'

Rpy2 & ggplot2: LookupError 'print.ggplot'

Unhindered by any pre-existing knowledge of R, Rpy2 and ggplot2 I would never the less like to create a scatterplot of a trivial table from Python.
To set this up I've just installed:
Ubuntu 11.10 64 bit
R version 2.14.2 (from r-cran mirror)
ggplot2 (through R> install.packages('ggplot2'))
rpy2-2.2.5 (through easy_install)
Following this I am able to plot some example dataframes from an interactive R session using ggplot2.
However, when I merely try to import ggplot2 as I've seen in an example I found online, I get the following error:
from rpy2.robjects.lib import ggplot2
File ".../rpy2/robjects/lib/ggplot2.py", line 23, in <module>
class GGPlot(robjects.RObject):
File ".../rpy2/robjects/lib/ggplot2.py", line 26, in GGPlot
_rprint = ggplot2_env['print.ggplot']
File ".../rpy2/robjects/environments.py", line 14, in __getitem__
res = super(Environment, self).__getitem__(item)
LookupError: 'print.ggplot' not found
Can anyone tell me what I am doing wrong? As I said the offending import comes from an online example, so it might well be that there is some other way I should be using gplot2 through rpy2.
For reference, and unrelated to the problem above, here's an example of the dataframe I would like to plot, once I get the import to work (should not be a problem looking at the examples). The idea is to create a scatter plot with the lengths on the x axis, the percentages on the Y axis, and the boolean is used to color the dots, whcih I would then like to save to a file (either image or pdf). Given that these requirements are very limited, alternative solutions are welcome as well.
original.length row.retained percentage.retained
1 1875 FALSE 11.00
2 1143 FALSE 23.00
3 960 FALSE 44.00
4 1302 FALSE 66.00
5 2016 TRUE 87.00
There were changes in the R package ggplot2 that broke the rpy2 layer.
Try with a recent (I just fixed this) snapshot of the "default" branch (rpy2-2.3.0-dev) for the rpy2 code on bitbucket.
Edit: rpy2-2.3.0 is a couple of months behind schedule. I just pushed a bugfix release rpy2-2.2.6 that should address the problem.
Although I can't help you with a fix for the import error you're seeing, there is a similar example using lattice here: lattice with rpy2.
Also, the standard R plot function accepts coloring by using the factor function (which you can feed the row.retained column. Example:
plot(original.length, percentage.retained, type="p", col=factor(row.retained))
Based on fucitol's answer I've instead implemented the plot using both the default plot & lattice. Here are both the implementations:
from rpy2 import robjects
#Convert to R objects
original_lengths = robjects.IntVector(original_lengths)
percentages_retained = robjects.FloatVector(percentages_retained)
row_retained = robjects.StrVector(row_retained)
#Plot using standard plot
r = robjects.r
r.plot(x=percentages_retained,
y=original_lengths,
col=row_retained,
main='Title',
xlab='Percentage retained',
ylab='Original length',
sub='subtitle',
pch=18)
#Plot using lattice
from rpy2.robjects import Formula
from rpy2.robjects.packages import importr
lattice = importr('lattice')
formula = Formula('lengths ~ percentages')
formula.getenvironment()['lengths'] = original_lengths
formula.getenvironment()['percentages'] = percentages_retained
p = lattice.xyplot(formula,
col=row_retained,
main='Title',
xlab='Percentage retained',
ylab='Original length',
sub='subtitle',
pch=18)
rprint = robjects.globalenv.get("print")
rprint(p)
It's a shame I can't get ggplot2 to work, as it produces nicer graphs by default and I regard working with dataframes as more explicit. Any help in that direction is still welcome!
If you don't have any experience with R but with python, you can use numpy or pandas for data analysis and matplotlib for plotting.
Here is a small example how "this feels like":
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
df = pd.DataFrame({'original_length': [1875, 1143, 960, 1302, 2016],
'row_retained': [False, False, False, False, True],
'percentage_retained': [11.0, 23.0, 44.0, 66.0, 87.0]})
fig, ax = plt.subplots()
ax.scatter(df.original_length, df.percentage_retained,
c=np.where(df.row_retained, 'green', 'red'),
s=np.random.randint(50, 500, 5)
)
true_value = df[df.row_retained]
ax.annotate('This one is True',
xy=(true_value.original_length, true_value.percentage_retained),
xytext=(0.1, 0.001), textcoords='figure fraction',
arrowprops=dict(arrowstyle="->"))
ax.grid()
ax.set_xlabel('Original Length')
ax.set_ylabel('Precentage Retained')
ax.margins(0.04)
plt.tight_layout()
plt.savefig('alternative.png')
pandas also has an experimental rpy2 interface.
The problem is caused by the latest ggplot2 version which is 0.9.0. This version doesn't have the function print.ggplot() which is found in ggplot2 version 0.8.9.
I tried to tinker with the rpy2 code to make it work with the newest ggplot2 but the extend of the changes seem to be quite large.
Meanwhile, just downgrade your ggplot2 version to 0.8.9

Categories

Resources