Matplotlib アプリケーション インターフェイス (API) #

Matplotlib には、2 つの主要なアプリケーション インターフェイス、またはライブラリの使用スタイルがあります。

  • Figure または Axes オブジェクトのメソッドを使用して他のアーティストを作成し、視覚化を段階的に構築する明示的な「Axes」インターフェイス。これは「オブジェクト指向」インターフェースとも呼ばれています。

  • 最後に作成された Figure と Axes を追跡し、ユーザーが必要と考えるオブジェクトに Artists を追加する暗黙的な "pyplot" インターフェイス。

さらに、多くのダウンストリーム ライブラリ (pandasxarray など) は、plotユーザーが を呼び出すことができるように、データ クラスに直接実装されたメソッドを提供しますdata.plot()

これらのインターフェースの違いは、特に Web 上のスニペットがいずれかを使用していたり​​、同じ例で複数のインターフェースを使用している場合は、少し混乱する可能性があります。ここでは、「pyplot」およびダウンストリーム インターフェイスが明示的な「Axes」インターフェイスにどのように関連しているかを指摘して、ユーザーがライブラリをより適切にナビゲートできるようにします。

ネイティブの Matplotlib インターフェース#

明示的な「軸」インターフェース#

「Axes」インターフェースは、Matplotlib の実装方法であり、多くのカスタマイズと微調整がこのレベルで行われます。

Figureこのインターフェイスは、クラスのインスタンスをインスタンス化し (fig以下)、そのオブジェクトでメソッド subplotsmethod (または同様のもの) を使用して 1 つまたは複数の Axesオブジェクトを作成し (ax以下)、Axes で描画メソッドを呼び出す (plotこの例) ことによって機能します。

import matplotlib.pyplot as plt

fig = plt.figure()
ax = fig.subplots()
ax.plot([1, 2, 3, 4], [0, 0.5, 1, 0.2])

(ソースコードpng )

../../_images/api_interfaces-1.png

各オブジェクトが明示的に参照され、次のオブジェクトを作成するために使用されるため、これを「明示的な」インターフェイスと呼びます。オブジェクトへの参照を保持することは非常に柔軟で、オブジェクトを作成した後、表示する前にオブジェクトをカスタマイズできます。

暗黙の「pyplot」インターフェース#

モジュールは、Figure と Axes の作成がユーザーのために行われる上記と同等のものを提供するために、ほとんどのプロット メソッドをシャドウpyplotし ます。Axes

import matplotlib.pyplot as plt

plt.plot([1, 2, 3, 4], [0, 0.5, 1, 0.2])

(ソースコードpng )

../../_images/api_interfaces-2.png

これは、特にインタラクティブな作業や単純なスクリプトを実行する場合に便利です。gcf現在の Figure への参照は、と現在の Axes を使用して取得できます gca。モジュールは Figureのpyplotリストを保持し、各 Figure はユーザーのために Figure の Axes のリストを保持するため、次のことが可能になります。

import matplotlib.pyplot as plt

plt.subplot(1, 2, 1)
plt.plot([1, 2, 3], [0, 0.5, 0.2])

plt.subplot(1, 2, 2)
plt.plot([3, 2, 1], [0, 0.5, 0.2])

(ソースコードpng )

../../_images/api_interfaces-3.png

次と同等です。

import matplotlib.pyplot as plt

plt.subplot(1, 2, 1)
ax = plt.gca()
ax.plot([1, 2, 3], [0, 0.5, 0.2])

plt.subplot(1, 2, 2)
ax = plt.gca()
ax.plot([3, 2, 1], [0, 0.5, 0.2])

(ソースコードpng )

../../_images/api_interfaces-4.png

明示的なインターフェイスでは、これは次のようになります。

import matplotlib.pyplot as plt

fig, axs = plt.subplots(1, 2)
axs[0].plot([1, 2, 3], [0, 0.5, 0.2])
axs[1].plot([3, 2, 1], [0, 0.5, 0.2])

(ソースコードpng )

../../_images/api_interfaces-5.png

なぜ明確にするのですか?#

によって参照されていない古い軸をバックトラックして操作する必要がある場合はどうなりますplt.gca()か? subplot簡単な方法の 1 つは、同じ引数で再度呼び出すことです。しかし、それはすぐにエレガントではなくなります。Figure オブジェクトを検査して Axes オブジェクトのリストを取得することもできますが、これは誤解を招く可能性があります (カラーバーも Axes です!)。おそらく最善の解決策は、作成するすべての Axes にハンドルを保存することですが、そうする場合は、最初にすべての Axes オブジェクトを単純に作成してみませんか?

plt.subplot最初のアプローチは、再度呼び出すことです。

import matplotlib.pyplot as plt

plt.subplot(1, 2, 1)
plt.plot([1, 2, 3], [0, 0.5, 0.2])

plt.subplot(1, 2, 2)
plt.plot([3, 2, 1], [0, 0.5, 0.2])

plt.suptitle('Implicit Interface: re-call subplot')

for i in range(1, 3):
    plt.subplot(1, 2, i)
    plt.xlabel('Boo')

(ソースコードpng )

../../_images/api_interfaces-6.png

2 つ目は、ハンドルを保存することです。

import matplotlib.pyplot as plt

axs = []
ax = plt.subplot(1, 2, 1)
axs += [ax]
plt.plot([1, 2, 3], [0, 0.5, 0.2])

ax = plt.subplot(1, 2, 2)
axs += [ax]
plt.plot([3, 2, 1], [0, 0.5, 0.2])

plt.suptitle('Implicit Interface: save handles')

for i in range(2):
    plt.sca(axs[i])
    plt.xlabel('Boo')

(ソースコードpng )

../../_images/api_interfaces-7.png

ただし、推奨される方法は、最初から明示的にすることです。

import matplotlib.pyplot as plt

fig, axs = plt.subplots(1, 2)
axs[0].plot([1, 2, 3], [0, 0.5, 0.2])
axs[1].plot([3, 2, 1], [0, 0.5, 0.2])
fig.suptitle('Explicit Interface')
for i in range(2):
    axs[i].set_xlabel('Boo')

(ソースコードpng )

../../_images/api_interfaces-8.png

サードパーティ ライブラリ「データ オブジェクト」インターフェイス#

一部のサードパーティ ライブラリは、データ オブジェクトのプロットを実装することを選択しました。たとえば、 、xarray、およびその他のサードパーティ ライブラリにdata.plot()見られます。説明のために、ダウンストリーム ライブラリはとデータを一緒に格納する単純なデータ コンテナを実装し、次にメソッドを実装する場合があります。pandasxyplot

import matplotlib.pyplot as plt

# supplied by downstream library:
class DataContainer:

    def __init__(self, x, y):
        """
        Proper docstring here!
        """
        self._x = x
        self._y = y

    def plot(self, ax=None, **kwargs):
        if ax is None:
            ax = plt.gca()
        ax.plot(self._x, self._y, **kwargs)
        ax.set_title('Plotted from DataClass!')
        return ax


# what the user usually calls:
data = DataContainer([0, 1, 2, 3], [0, 0.2, 0.5, 0.3])
data.plot()

(ソースコードpng )

../../_images/api_interfaces-9.png

したがって、ライブラリはすべての核心をユーザーから隠すことができ、多くの場合、適切なラベル、カラーマップの選択、およびその他の便利な機能を使用して、データ型に適した視覚化を行うことができます。

ただし、上記では、ライブラリが提供したタイトルが気に入らなかった可能性があります。ありがたいことに、彼らはplot()メソッドから Axes を返し、明示的な Axes インターフェイスを理解すると 、タイトルをカスタマイズするために : を呼び出すことができます。ax.set_title('My preferred title')

plot多くのライブラリでは、メソッドがオプションのax 引数を受け入れることもできます。これにより、配置しておそらくカスタマイズした Axes にビジュアライゼーションを配置できます。

まとめ#

全体として、明示的な「Axes」インターフェースを理解することは有益です。これは、最も柔軟性が高く、他のインターフェースの基礎となるからです。ユーザーは通常、明示的なインターフェイスにドロップダウンして、基になるオブジェクトを操作する方法を理解できます。明示的なインターフェースはセットアップが少し冗長になる可能性がありますが、複雑なプロットは、暗黙的な「pyplot」インターフェースを使用しようとするよりも単純になることがよくあります。

ノート

pyplot両方のインターフェイスをインポートすると、混乱することがあります。現在、このpyplotモジュールは「pyplot」インターフェースを実装していますが、トップレベルの Figure および Axes 作成メソッドも提供し、最終的にグラフィカル ユーザー インターフェース (使用されている場合) をスピンアップします。選択したインターフェイスに関係なく、これpyplotは依然として必要です。

同様に、パートナー ライブラリによって提供される宣言型インターフェイスは、「Axes」インターフェイスによってアクセス可能なオブジェクトを使用し、多くの場合、これらを引数として受け入れるか、メソッドから返します。通常、明示的な「Axes」インターフェイスを使用して、デフォルトの視覚化のカスタマイズを実行するか、データを NumPy 配列にアンパックして直接 Matplotlib に渡すことが不可欠です。

付録: データ構造を持つ「軸」インターフェース#

ほとんどのメソッドでは、データオブジェクトをメソッドにAxes渡し、引数を文字列として指定することで、さらに別の API アドレッシングが可能 になります。

import matplotlib.pyplot as plt

data = {'xdat': [0, 1, 2, 3], 'ydat': [0, 0.2, 0.4, 0.1]}
fig, ax = plt.subplots(figsize=(2, 2))
ax.plot('xdat', 'ydat', data=data)

(ソースコードpng )

../../_images/api_interfaces-10.png

付録: "pylab" インターフェース#

もう 1 つ、非常に推奨されていないインターフェイスがあり、それは基本的に. これにより、ユーザーは単純に を呼び出すことができます。便利ではありますが、ユーザーが無意識のうちに変数に pyplot メソッドと同じ名前を付けた場合、これは明らかな問題を引き起こす可能性があります。from matplotlib.pyplot import *plot(x, y)