Matplotlib におけるカスタムメルカトル緯度スケール

PythonPythonBeginner
オンラインで実践に進む

This tutorial is from open-source community. Access the source code

💡 このチュートリアルは英語版からAIによって翻訳されています。原文を確認するには、 ここをクリックしてください

はじめに

Matplotlib は、Python 用の強力なデータ可視化ライブラリです。これは、データのプロットにいくつかの組み込みスケールを提供しますが、特定のユースケースに合わせたカスタムスケールが必要な場合もあります。この実験では、緯度データにメルカトル投影を使用するカスタムスケールを作成する方法を紹介します。

VM のヒント

VM の起動が完了したら、左上隅をクリックしてノートブックタブに切り替え、Jupyter Notebook を使って練習しましょう。

Jupyter Notebook の読み込みには数秒かかる場合があります。Jupyter Notebook の制限により、操作の検証は自動化できません。

学習中に問題が発生した場合は、Labby にお問い合わせください。セッション後にフィードバックを提供してください。すぐに問題を解決いたします。

必要なライブラリをインポートする

必要なライブラリをインポートして始めましょう。

import numpy as np
from numpy import ma

from matplotlib import scale as mscale
from matplotlib import transforms as mtransforms
from matplotlib.ticker import FixedLocator, FuncFormatter

MercatorLatitudeScale クラスを定義する

次に、カスタムスケールを実装する MercatorLatitudeScale クラスを定義します。このクラスは mscale.ScaleBase から継承します。

class MercatorLatitudeScale(mscale.ScaleBase):
    """
    メルカトル投影における緯度のスケーリングに使用されるシステムを使って、
    -pi/2 から pi/2 (-90 度から 90 度) の範囲のデータをスケーリングします。

    スケール関数:
      ln(tan(y) + sec(y))

    逆スケール関数:
      atan(sinh(y))

    メルカトルスケールは +/- 90 度で無限大になる傾向があるため、
    ユーザー定義の閾値があり、これより上または下では何もプロットされません。
    このデフォルトは +/- 85 度です。

    __ https://en.wikipedia.org/wiki/Mercator_projection
    """

MercatorLatitudeTransform クラスを実装する

MercatorLatitudeScale クラスの中で、実際にデータを変換する MercatorLatitudeTransform クラスを定義します。このクラスは mtransforms.Transform から継承します。

    class MercatorLatitudeTransform(mtransforms.Transform):
        ## 定義する必要のある値のメンバーが 2 つあります。
        ## ``input_dims`` と ``output_dims`` は、変換の入力次元数と出力次元数を指定します。
        ## これらは、変換フレームワークによってエラーチェックに使用され、互換性のない変換が一緒に接続されるのを防ぎます。
        ## 定義上、分離可能で 1 次元のみを持つスケールの変換を定義する場合、これらのメンバーは常に 1 に設定する必要があります。
        input_dims = output_dims = 1

        def __init__(self, thresh):
            mtransforms.Transform.__init__(self)
            self.thresh = thresh

        def transform_non_affine(self, a):
            """
            この変換は、numpy 配列を受け取り、変換されたコピーを返します。
            メルカトルスケールの範囲はユーザー指定の閾値によって制限されるため、入力配列はマスクされて有効な値のみを含む必要があります。
            Matplotlib はマスクされた配列を処理し、プロットから範囲外のデータを削除します。
            ただし、返される配列は入力配列と同じ形状でなければなりません。
            なぜなら、これらの値は他の次元の値と同期を保つ必要があるからです。
            """
            masked = ma.masked_where((a < -self.thresh) | (a > self.thresh), a)
            if masked.mask.any():
                return ma.log(np.abs(ma.tan(masked) + 1 / ma.cos(masked)))
            else:
                return np.log(np.abs(np.tan(a) + 1 / np.cos(a)))

        def inverted(self):
            """
            このメソッドをオーバーライドして、Matplotlib がこの変換の逆変換を取得する方法を知らせます。
            """
            return MercatorLatitudeScale.InvertedMercatorLatitudeTransform(
                self.thresh)

逆メルカトル緯度変換クラスを実装する

このスケールの逆変換を取得するために使用される 逆メルカトル緯度変換 クラスも定義します。

    class InvertedMercatorLatitudeTransform(mtransforms.Transform):
        input_dims = output_dims = 1

        def __init__(self, thresh):
            mtransforms.Transform.__init__(self)
            self.thresh = thresh

        def transform_non_affine(self, a):
            return np.arctan(np.sinh(a))

        def inverted(self):
            return MercatorLatitudeScale.MercatorLatitudeTransform(self.thresh)

カスタムスケールを登録する

mscale.register_scale を使って、Matplotlib にカスタムスケールを登録します。

mscale.register_scale(MercatorLatitudeScale)

カスタムスケールを使用する

これで、プロットでカスタムスケールを使用できるようになりました。ここでは、メルカトル投影における緯度データにカスタムスケールを使用する例を示します。

if __name__ == '__main__':
    import matplotlib.pyplot as plt

    t = np.arange(-180.0, 180.0, 0.1)
    s = np.radians(t)/2.

    plt.plot(t, s, '-', lw=2)
    plt.yscale('mercator')

    plt.xlabel('Longitude')
    plt.ylabel('Latitude')
    plt.title('Mercator projection')
    plt.grid(True)

    plt.show()

まとめ

この実験では、Matplotlib でメルカトル投影を使用して緯度データ用のカスタムスケールを作成する方法を学びました。MercatorLatitudeScaleMercatorLatitudeTransform クラスを定義し、mscale.register_scale を使って Matplotlib にカスタムスケールを登録しました。また、メルカトル投影における緯度データにカスタムスケールを使用する例も示しました。