matplotlibで等高線やら何やらのプロット

今回は等高線や、疑似カラープロット(?)に挑戦です。
今までと違い、x, yのデータの他にz方向のデータを持っています。


以前のお話はこちら
matplotlibでグラフを書く - たこ焼き食べた.net

疑似カラープロット(?)

行列の作り方

これは以下の等高線などでも使う知識なので重要です。
今回挑戦するx, y, zの3軸の情報を持つグラフは、今までと若干行列の与え方が異なります。
例えば、5*5の行列をプロットするとすると以下の行列が必要となります。

このように、x, y, zがそれぞれ、5*5の情報を持つ必要があります。
通常、x, y, zは

x = arange(5)
y = arange(5)
Z = array([[24, 32, 12, 16, 21],
           [23, 24, 25, 26, 27],
           [43, 36, 32, 26, 25],
           [30, 32, 25, 21, 20],
           [20, 32, 23, 20, 14]])

のように、x, yは1次元の配列かと思います。
従ってこれを2次元の配列に変換してあげる必要があります。
これには、meshgrid関数を用います。

X, Y = meshgrid(x, y)

このようにすると、X, Yに、x, yを2次元に変換した配列が代入されます。
このように、3次元の情報を持つグラフでは、
X, Yと、上に示したZのような2次元配列を利用してプロットしていきます。

pcolor関数

pcolor関数を使うことで、疑似カラープロットを描画することができます。
pcolor関数は以下のような動作をします。

このように、ある点をプロットする時は、その要素とその次の要素で囲まれた領域を塗り潰します。
というわけで、例えば、5*5の行列をプロットしたいときは、x, yは6個の要素を持っている必要があります。
間違いやすいので注意してください。
(というか前節の図も間違って4*4のグラフになってしまっていますね。。。)


例えば、以下のようにプロットすることができます。

from pylab import *

N = 5
x = arange(N+1)
y = arange(N+1)
Z = array([[24, 32, 12, 16, 21],
           [23, 24, 25, 26, 27],
           [43, 36, 32, 26, 25],
           [30, 32, 25, 21, 20],
           [20, 32, 23, 20, 14]])

X, Y = meshgrid(x, y)
pcolor(X, Y, Z)
colorbar

show()


ちなみに、colorbar関数を付けることで、カラーバーを表示することができます。
値と色の関係を示しますのでほぼ必須かと思います。

サンプル

もうちょっと複雑な図を以下に載せてみます。
上のやつは四角がはっきりしていて地味ですし。。。

from pylab import *

x = arange(0, 10.1, 0.1)
y = arange(0, 10.1, 0.1)

X, Y = meshgrid(x, y) 
Z = cos(X) + cos(Y)

pcolor(X, Y, Z)
colorbar()

show()

上述のような理由で、x=10, y=10のときのZがプロットされていないが、今回は無視。。。
というわけで以下のようなグラフができました。

色合いを変える。

色合いの設定を変えることができます。
以下のような関数を使えば簡単だと思います。

  • autumn
  • bone
  • cool
  • copper
  • flag
  • gray
  • hot
  • hsv
  • jet
  • pink
  • prism
  • spring
  • summer
  • winter
  • spectral

結構たくさんありますね。
以下に、pinkの例を示します。

from pylab import *

x = arange(0, 10.1, 0.1)
y = arange(0, 10.1, 0.1)

X, Y = meshgrid(x, y) 
Z = cos(X) + cos(Y)

pcolor(X, Y, Z)
colorbar()
pink()

show()

等高線

疑似カラープロットの話を理解していれば簡単です。
contour関数を用いて、

contour(X, Y, Z)

でプロットできます。
なお、等高線の数は以下のように引数を与えてあげることで指定できます。

contour(X, Y, Z, V)

この場合、等高線の数はV個になります。


というわけでサンプル。
カラーマップは先程と同様に指定できます。

from pylab import *

x = arange(0, 10.1, 0.1)
y = arange(0, 10.1, 0.1)

X, Y = meshgrid(x, y) 
Z = cos(X) + cos(Y)

contour(X, Y, Z)
colorbar()
spring()

show()

grayバージョン