本節書摘來異步社群《python資料可視化程式設計實戰》一書中的第5章,第5.5節,作者:【愛爾蘭】igor milovanović,更多章節内容可以通路雲栖社群“異步社群”公衆号檢視。
python資料可視化程式設計實戰
使用opengl的動機來源于cpu處理能力的限制,限制展現在當我們面臨一項要可視化成千上萬個資料點的工作,并且要求其快速執行(有時甚至是實時的)的時候。
現代計算機擁有強大的gpu用于加速與可視化相關的計算(比如遊戲)。它們沒有理由不能用于科學相關的可視化。
實際上,編寫硬體加速的軟體至少有一個缺點。就硬體的依賴而言,現代圖形卡要求有專有的驅動,有時候驅動在目标平台/機器(例如使用者的筆記本)上是無法使用的;即使是可用的,有時候你也不想呆在那花大把的時間去安裝驅動所依賴的軟體,相反,你想把時間花費在展示你的發現,并示範你的研究成果上。雖然這并不會成為編寫硬體加速軟體的障礙,但是你還是需要考慮一下這件事情,并且衡量一下在項目中引入這個複雜性的成本和收益。
解釋完缺點後,我們可以對硬體加速可視化說“是”,可以對opengl,這一圖形加速的工業标準說“是”。
我們将使用opengl來完成本節的内容,因為它是跨平台的,是以所有的例子應該在linux、mac或者windows上都是工作的,就像我們所示範的那樣。這裡假定你已經安裝了所需的硬體和作業系統級别的驅動。
如果你從來沒有使用過opengl,現在我們将做一個快速的介紹來幫助你了解。但是要真正的了解opengl,至少要閱讀并了解一整本書。opengl是一個規範,而不是一個實作,是以opengl本身并沒有任何實作代碼,所有的實作是遵循該規範而開發的庫。這些庫是跟随你的作業系統,或者由如nvidia或者amd/ati等不同的顯示卡廠商釋出的。
此外,opengl隻關注圖形渲染而不是動畫、定時和其他複雜的事情,這些事情是留給其他庫來完成的。
因為opengl是一個圖形渲染庫,是以它不知道我們在螢幕上繪制的是什麼。它不關心我們畫的是否是一隻貓、一個球,或者一條線,還是所有這些對象。是以,要移動一個已經渲染的對象,需要清除并重繪整個圖像。為了讓某個物體動起來,我們需要很快地循環繪制和重繪所有内容,并把它顯示給使用者,這樣使用者就認為他/她正在觀看一個動畫。
在機器上安裝opengl是一件和平台相關的過程。在mac os x上,opengl的安裝通過系統更新來完成,但是開發庫(所謂的“頭檔案”)是xcode開發包的一部分。
在windows系統上,最好的方式是安裝電腦的顯示卡廠商的最新顯示卡驅動程式。opengl可能并不需要它們就可以工作,但那樣的話你就很可能失去了原版驅動程式的最新特性。
在linux平台上,如果你不反對安裝閉源軟體,在作業系統發行版自身的軟體管理器中,或者顯示卡廠商網站上的二進制安裝檔案,都提供了可供下載下傳的特定廠商的驅動。mesa3d幾乎一直都是opengl的标準實作,它也是最有名的opengl實作,使用xorg來為linux、freebsd和類似作業系統的opengl提供支援。
基本上,在debian/ubuntu系統中,應當安裝下列軟體包及其依賴。
$ sudo apt-get install libgl1-mesa-dev libgl-mesa-dri
然後,你就可以使用一些開發庫和/或者架構來實際地編寫opengl支援的應用程式了。
我們在這裡隻關注python中的opengl繪圖,是以我們将回顧在python中使用最多的一些建構在opengl之上的庫和架構。我們會提到matplotlib及其目前和将來對opengl的支援。
mayavi:這是一個專門用于3d的庫。
pyglet:這是一個純python的圖形庫。
glumpy:這是一個建構在numpy之上的快速圖形渲染庫。
pyglet和opengl:這是用來可視化大資料(百萬級資料點)的。
專業化的項目mayavi是一個功能全面的3d圖形庫,它主要用于進階3d渲染。它包含在已經提到的 python包中,如epd(雖然沒有免費許可)。這也是在windows和mac os x作業系統上的推薦安裝方式。在linux平台上,也可以通過pip輕松地安裝,代碼如下。
import numpy
from mayavi.mlab import *
n_mer, n_long = 6, 11
pi = numpy.pi
dphi = pi/1000.0
phi = numpy.arange(0.0, 2pi + 0.5dphi, dphi, 'd')
mu = phi*n_mer
x = numpy.cos(mu)(1+numpy.cos(n_longmu/n_mer)*0.5)
y = numpy.sin(mu)(1+numpy.cos(n_longmu/n_mer)*0.5)
z = numpy.sin(n_longmu/n_mer)0.5
l = plot3d(x, y, z, numpy.sin(mu), tube_radius=0.025,
colormap='spectral')
ms = l.mlab_source
for i in range(100):
in [1]: import mayavi.mlab
in [2]: mayavi.mlab.test_simple_surf??
type: function
string form:
file:/usr/lib/python2.7/dist-packages/mayavi/tools/helper_
functions.py
definition: mayavi.mlab.test_simple_surf()
source:
def test_simple_surf():
import pyglet
window = pyglet.window.window()
image = pyglet.resource.image('kitten.jpg')
@window.event
def on_draw():
pyglet.app.run()
sudo apt-get install python-opengl
sudo pip install scipy
sudo pip install glumpy