减少散点图的文件大小

问题描述:

我正在尝试减小散点图的文件大小。我的代码如下所示:减少散点图的文件大小

plt.scatter(a1,b1) 
plt.savefig('test.ps') 

其中A1,B1是大小为400,000这样的阵列,它给7.8MB的文件大小。

我已经试过此块的代码之前添加

plt.rcParams['path.simplify'] = True 

,但文件仍然是7.8MB。这是一个问题,它如何保存为“.ps”文件或其他问题?

一种方法是使用plot代替scatter(你仍然可以生产使用plot使用'o'参数散点图),并使用rasterized关键字参数,就像这样:

import numpy as np 
import matplotlib.pyplot as plt 

a1,b1 = np.random.randn(400000,2).T #mock data of similar size to yours 
plt.plot(a1,b1,'o',rasterized=True) 
plt.savefig("test.ps") 

这应该显著减少输出文件的大小。文字和线条艺术将保持矢量,只有点被光栅化,所以这是一个很好的折衷。

但是,根据您希望达到的目标,可能会更好地对您的数据进行直方图绘制(例如pyplot.hist2dpyplot.hexbin)。

+0

但是这种解决方案失去在第一时间使用类似的PostScript基于矢量格式的所有优点,不是吗? – Schmuddi

+1

该方法仅对点进行栅格化,文本和线条艺术停留矢量。确实,你不能随意缩放,但我想在图形的信息内容和内存大小之间必须有一些折衷。对我而言,这往往是一个有用的妥协。 –

我认为这是由于PostScript格式造成的,没有什么可以改变的。让我们来做数学运算:

7.8MB类似于7.8 * 1024 * 1024 = 8,178,892.8。假设你的散点图中有40万点,这意味着如果你的文件中没有其他东西(即没有图例,没有注释等),你的文件会为散点图中的每个点分配20个字节。

现在,我不是PostScript专家,但看着输出test.ps,所使用的命令来绘制圆圈的PostScript看起来是这样的:

[x] [y] o 

其中x和y是各点的坐标。由于这些是浮点值,所以信息的确加起来可以达到15个字节,这与我上面的猜测并不相距太远。

所以是的,文件大小是由PostScript文件的性质引起的,它为散点图中的每个400,000点存储了相当多的信息。

您可以按照@AngusWilliams的答案中的建议将散点图存储为光栅化图像,这将导致文件较小。但是,您将失去基于矢量的文件格式的优势:在任何分辨率下无损缩放。

如果你不需要这种基于矢量的文件格式的优点,你甚至可以使用另一种文件格式,如.png,它比通过PostScript包含光栅化信息通常在压缩图像方面做得更好。

你可以考虑使用例如hexbin - 当你有很多点时,我特别喜欢这个,因为它更好地表明你的数据集中在哪里。例如:

import numpy as np 
import matplotlib.pylab as pl 

x = np.random.normal(size=40000) 
y = np.random.normal(size=40000) 

pl.figure() 

pl.subplot(121) 
pl.scatter(x, y) 
pl.xlim(-4,4) 
pl.ylim(-4,4) 

pl.subplot(122) 
pl.hexbin(x, y, gridsize=40) 
pl.xlim(-4,4) 
pl.ylim(-4,4) 

enter image description here

从左侧图中,我会得出的结论是x,y = {-3,3}之间的点的分布是大致相等的,这显然不是这样。

http://matplotlib.org/examples/pylab_examples/hexbin_demo.html

+0

我已经在我的回答中提出了这个问题... –

+0

糟糕,错过了......无论如何,我将它留在这里作为一个例子,说明它如何阐明密集点的可视化。 – Bart