Matplotlibで行列を回転させる

Oct 29 2020

私は回転(これは変更することができたが、N = 20)anxn行列を30度右方向matplotlibの使用の変換方法を。

回転はベースからではなくトップから実行されるため、エラーが表示されますnp.flip()またはを介してインデックスを反転しようとしましたax.imshow(origin = 'lower')が、三角形も反転するため、変換の原点を設定する方法を見つける必要があります。

Defintley、これは私が取得したいものです

対角行列に一致する小さな正方形が三角形に変わることに注意してください。これはできますか?たぶん、半分のピクセルを返すimshowメソッドによってですか?残りのピクセルは同じままです(変形した小さな正方形)。

マトリックス(開始点)を生成するためのコードは次のとおりです。

import numpy as np
import matplotlib.pyplot as plt
import matplotlib.transforms as mtransforms

matrix = np.random.rand(20,20)

# Generate a boolean matrix (same shape than 'matrix') and select lower triangle values:

condition = np.tril(np.ones((matrix.shape))).astype(np.bool)
triangle = np.where(condition, matrix, np.nan)

fig, ax = plt.subplots(figsize = (8,8))

ax.imshow(triangle, cmap = 'Spectral')

そして、これがそれを回転させようとしているコードです

im = ax.imshow(matrix, cmap = 'Spectral')
im.set_transform(mtransforms.Affine2D().skew(30, 0) + ax.transData)
ax.plot(transform = trans_data)

三角グラフは補間操作によって表されるため、MatplotlibのTriangleクラスを使用していません。また、元の行列値を表したいと考えています。

誰かの助けを本当に感謝します。事前にどうもありがとうございました。

回答

3 tmdavison Oct 29 2020 at 13:39

スキュー変換の原点を変更する代わりに、x方向の平行移動でチェーンして、探している変換を実現できます。

skew変換はラジアン単位の角度をとることに注意してください(度で使用していました)。skew_deg度で作業したい場合は同等の変換がありますが、ここではラジアンで作業します。

また、底辺と高さが両方とも20(またはNを選択したもの)に等しい二等辺三角形が必要だと思います。必要な角度は30度ではなく、実際にはarctan(1/2)(= 26.56)です。度)。

x方向に移動する必要がある量はxtrans = N * np.tan(angle)です。

matplotlibで変換を簡単に連鎖させることができます。ここでは、最初にスキューしてから、次のように変換できます。

mtransforms.Affine2D().skew(-angle, 0).translate(xtrans, 0)

このスクリプトは、Nの任意の値に対して機能することに注意してください。

import numpy as np
import matplotlib.pyplot as plt
import matplotlib.transforms as mtransforms

N = 20
matrix = np.random.rand(N, N)

# Generate a boolean matrix (same shape than 'matrix') and select lower triangle values:

condition = np.tril(np.ones((matrix.shape))).astype(np.bool)
triangle = np.where(condition, matrix, np.nan)

fig, ax = plt.subplots(figsize = (8,8))

im = ax.imshow(triangle, cmap = 'Spectral')

angle = np.arctan(1/2)
xtrans = N * np.tan(angle)
im.set_transform(mtransforms.Affine2D().skew(-angle, 0).translate(xtrans, 0) + ax.transData)

ax.set_xlim(-0.5, N + 0.5)
plt.show()

N = 20の場合

そしてN = 30の場合

MiguelGonzalez Oct 30 2020 at 10:20

最終的に、y軸をスケーリングする正三角形を取得します。ここにコードを示します。

したがって、行列を正三角形に変換することができます。これは私の前の質問に答えるものです。

import numpy as np
import matplotlib.pyplot as plt
import matplotlib.transforms as mtransforms
import matplotlib

bins = 50
Z = np.random.rand(bins, bins)

# Generate a boolean matrix (same shape than 'matrix') and select lower triangle values:
condition = np.tril(np.ones((Z.shape))).astype(np.bool)
Z = np.where(condition, Z, np.nan)

fig, ax = plt.subplots(figsize = (8,8))
im = ax.imshow(Z, cmap = 'Spectral')

# Required angles (in Rad)
alpha = np.arctan(1/2)        # 26 deg angle, in radians.
beta = np.arctan(np.pi/6)     # 30 deg angle, in radians.

# Coefficients:
xtrans = np.sin(beta) * bins
scale_y = np.cos(beta)     

# Transformation:
im.set_transform(mtransforms.Affine2D().skew      (-alpha, 0)
                                       .scale     (1,scale_y)
                                       .translate (xtrans, 0) 
                                        + ax.transData)

ax.set_ylim(bins,-5)
ax.set_xlim(-5,bins)

plt.show()