matplotlib 使用cmap和plt.imshow为图着色时避免边线或重叠

bkhjykvo  于 2023-11-22  发布在  其他
关注(0)|答案(1)|浏览(131)

如何将图从红色连续着色为绿色(平滑变化)基于沿着y轴的4种不同的样式,使用cmap,其中第一部分和最后一部分分别用恒定的红色和绿色着色。在这方面,如果可以的话,我想使用plt.imshow。我为此编写了以下代码,从其他帖子中得到启发,并基于我的需要,但它会在部分之间产生一些重叠或边缘颜色。这些部分必须被着色为第一部分是红色(cmap的第一种颜色),第二部分必须从红色平滑地变为黄色,第三部分必须从最后一个红色继续变为绿色,最后一部分必须始终是绿色:

import numpy as np
import matplotlib.pyplot as plt

plt.rcParams["figure.figsize"] = (19.2, 9.6)

Diam_P = 0.4
ylim = 7

plt.imshow(np.interp(np.linspace(0, 3 * Diam_P, 1), [0, 1], [0, 0]).reshape(-1, 1),
           cmap='hsv', vmin=0, vmax=1, extent=[0, 180, 0, 3 * Diam_P], origin='lower',
           interpolation='bilinear', aspect='auto', zorder=-1, alpha=0.7)
plt.imshow(np.interp(np.linspace(3 * Diam_P, 2, 10000), [3 * Diam_P, 2], [0, 0.15]).reshape(-1, 1),
           cmap='hsv', vmin=0, vmax=1, extent=[0, 180, 3 * Diam_P, 2], origin='lower',
           interpolation='bilinear', aspect='auto', zorder=-1, alpha=0.7)
plt.imshow(np.interp(np.linspace(2, 3, 20000), [2, 3], [0.15, 0.24]).reshape(-1, 1),
           cmap='hsv', vmin=0, vmax=1, extent=[0, 180, 2, 3], origin='lower',
           interpolation='bilinear', aspect='auto', zorder=-1, alpha=0.7)
plt.imshow(np.interp(np.linspace(3, ylim, 1), [3, ylim], [0.24, 0.24]).reshape(-1, 1),
           cmap='hsv', vmin=0, vmax=1, extent=[0, 180, 3, ylim], origin='lower',
           interpolation='bilinear', aspect='auto', zorder=-1, alpha=0.7)

plt.xlim(0, 70)
plt.ylim(0, ylim)
plt.savefig("test2.png", dpi=600)
plt.show()

字符串


的数据
问题是图上出现的边线或重叠,如图所示,颜色未连续从黄色变为绿色(开始为深绿色,然后为浅绿色,与预期不符):



我将感谢解决这些问题的解决方案.

n9vozmp4

n9vozmp41#

在波段重叠的地方,alpha混合会产生一条较暗的线。你可以通过不使用alpha或者一次性绘制图像来避免这种情况。

使用'hsv'和拉伸图像

要一次性绘制所有内容,请执行以下操作:

  • 从一个线性“图像”开始,从0ylim有足够的细分
  • 使用np.interpMap值:
  • 0到“color”0(“hsv”中的红色)
  • 3 * Diam_P也可以“颜色”0
  • 2到“颜色”0.15(黄色)
  • 3至“颜色”0.24(绿色)
  • ylim也可以“颜色”0.15
  • 使用vmin=0vmax=1cmap='hsv'通过imshow绘制Map图像
import matplotlib.pyplot as plt
import numpy as np

Diam_P = 0.4
ylim = 7
linear_img = np.linspace(0, ylim, 1000).reshape(-1, 1)
stretched_img = np.interp(linear_img,
                          [0, 3 * Diam_P, 2, 3, ylim],
                          [0, 0, 0.15, 0.24, 0.24])
plt.imshow(stretched_img, cmap='hsv',
           vmin=0, vmax=1, extent=[0, 180, 0, ylim], origin='lower',
           interpolation='bilinear', aspect='auto', zorder=-1, alpha=0.7)
plt.show()

字符串
x1c 0d1x的数据

使用线性图像的拉伸色彩Map表

或者,您可以使用LinearSegmentedColormap将边界Map到3种给定颜色。对于此Map,边界首先需要转换为0-1范围。这将创建从给定红色到给定黄色再到给定绿色的线性Map,而不需要经过“HSV”色彩Map表中的颜色。(Map是RGB空间的线性Map,而不是色调。)

import matplotlib.pyplot as plt
from matplotlib.colors import LinearSegmentedColormap
import numpy as np

Diam_P = 0.4
ylim = 7

linear_img = np.linspace(0, 1, 1000).reshape(-1, 1)
red, yellow, green = plt.get_cmap('hsv')([0, 0.15, 0.24])
cmap = LinearSegmentedColormap.from_list('',
                                         [(0, red),
                                          (3 * Diam_P / ylim, red),
                                          (2 / ylim, yellow),
                                          (3 / ylim, green),
                                          (1, green)])
plt.imshow(linear_img, cmap=cmap,
           extent=[0, 180, 0, ylim], origin='lower',
           interpolation='bilinear', aspect='auto', alpha=0.7, zorder=-1)
plt.show()


相关问题