#matplotlib #seaborn #matplotlib-basemap
#matplotlib #seaborn #matplotlib-базовая карта
Вопрос:
При использовании LinearSegmentedColormap в документации Matplotlib упоминается аргумент colors, который
цвета: массивоподобные цвета или массивоподобные цвета (значение, цвет). Если заданы только цвета, они отображаются на равном расстоянии от диапазона [0,1]; т. е. 0 соответствует цветам [0], а 1 соответствует цветам [-1]. Если заданы пары (значение, цвет), то сопоставление осуществляется от значения к цвету. Это может быть использовано для неравномерного разделения диапазона.
У меня есть следующие цвета [‘малиновый’, ‘коричневый’, ‘лаймовый’, ‘коричневый’, ‘малиновый’], и я хочу разделить диапазон неравномерно таким образом:
(-1, -0,5) : ‘малиновый’
(-0.5, -0.15) : «коричневый»
(-0.15, 0.15): ‘lime’
(0,15, 0,5) : «коричневый»
(0,5, 1) : «малиновый»
Я попытался передать аргумент colors в формате: [(-1, ‘crimson’), (-0.5, ‘brown), (-0.15, ‘lime’), (0.15, ‘brown), (0.5, ‘crimson’)] но получил ошибку. Я что-то упускаю?
Ответ №1:
Для достижения описанной цветовой сегментации вы могли бы объединить LinearSegmentedColormap.from_list('', colors, len(colors))
с BoundaryNorm
. Обратите внимание, что вам нужно 6 границ для 5 цветов.
Работа с (value, color)
парами для LinearSegmentedColormap
кажется немного громоздкой, поскольку значения должны быть нормализованы, чтобы строго переходить от 0 к 1. Это было бы более подходящим, если вам нужен непрерывный диапазон цветов и вы хотите установить определенный цвет в определенной позиции (а не в определенном диапазоне).
from matplotlib import pyplot as plt
from matplotlib.colors import LinearSegmentedColormap, BoundaryNorm
import numpy as np
bounds = [-1, -0.5, -0.15, 0.15, 0.5, 1]
colors = ['crimson', 'brown', 'lime', 'brown', 'crimson']
cmap = LinearSegmentedColormap.from_list('', colors, N=len(colors))
norm = BoundaryNorm(bounds, ncolors=len(colors), )
x = np.random.uniform(0, 1, 100)
y = np.random.uniform(-1, 1, 100)
plt.scatter(x, y, c=y, cmap=cmap, norm=norm)
plt.colorbar()
plt.show()
Обратите внимание, что вы можете использовать plt.colorbar(spacing='proportional')
для отображения больших фрагментов цвета в больших диапазонах. По умолчанию используется spacing='uniform'
с равным пространством для каждого цвета.
PS: Что касается нового вопроса, пользовательская гладкая цветовая карта может быть создана с помощью (value, color)
списка для LinearSegmentedColormap
и установки дополнительных границ.
from matplotlib import pyplot as plt
from matplotlib.colors import LinearSegmentedColormap
import numpy as np
bounds = [-1, -0.5, -0.499, -0.15, -0.149, 0.0, 0.149, 0.15, 0.499, 0.5, 1]
colors = ['crimson', 'crimson', 'brown', 'brown', 'limegreen', 'lime', 'limegreen', 'brown', 'brown', 'crimson', 'crimson']
norm = plt.Normalize(bounds[0], bounds[-1])
cmap = LinearSegmentedColormap.from_list('', [(norm(b), c) for b, c in zip(bounds, colors)], N=256)
x = np.random.uniform(0, 1, 100)
y = np.random.uniform(-1, 1, 100)
plt.scatter(x, y, c=y, cmap=cmap, norm=norm)
plt.colorbar()
plt.show()
Комментарии:
1. Спасибо за вашу помощь. Есть ли способ сделать цвет темнее внутри той же цветовой категории, другими словами, точка со значением 0,01 будет светло-желтой, а точка с 0,14 будет темно-желтой? Спасибо 🙂