У меня есть pandas.dataframe
, который выглядит следующим образом:
columns 0 1 2 3 4 5
A A A A B B
B B B C C D
D D E E F F
Я хочу построить это с помощью pyplot.imshow()
, указав следующую цветовую карту:
color_dict = {
"A": "#DA291E",
"B": "#83DF39",
"C": "#E8132d",
"D": "#008933",
"E": "#006CB3",
"F": "#52BFEC"
}
Если бы я былпостроение bar
или scatter
Я мог бы просто позвонить с аргументом color=a_list_of_colors
, но это не работает с imshow()
.
Вместо этого мне нужно позвонить с cmap
, но, насколько я понимаю, невозможно создать карту, в которой определенный цвет сопоставляется со значением.
Это означает, что мне нужно создать такую цветовую карту:
from matplotlib.colors import ListedColormap
_colors = ["#DA291E", "DA291E", "DA291E", "DA291E"
"#83DF39", "#83DF39", "#83DF39", "#83DF39", "#83DF39", #...and so on]
cmap = ListedColormap(_colors, name="custom_cmap")
Но есть ли лучший способ сделать это?
Я думал, что смогуреализовать описанный выше метод, но по какой-то причине он не работает, и я не могу понять, почему.
Я начинаю с создания color_list на основе длинной series
версии моего df
выше изатем преобразуйте этот список в цветовую карту:
color_list = list(series.map(color_dict))
custom_cmap = ListedColormap(color_list, name="custom_cmap")
Длинный series
в основном выглядит следующим образом:
A
A
A
A
B
B
B
B
B
C
#...and so on
Пятый элемент в моем df
равен B
, и когдаЯ печатаю custom_cmap.__dict__.colors[4]
, я получаю #83DF39
, что соответствует строковому значению B
в моем df
.Таким образом, отображение правильное.
Проблема возникает, когда я звоню plt.imshow()
с cmap=custom_cmap
, так как он не следует cmap
- некоторые значения получают неправильный цвет.
MyПервой мыслью было, что я испортил порядок, то есть color_list
не следовал порядку df
, но это так.
Выше df
содержит 18 значений, а color_list тоже,Последнее значение в df
- это F
, что означает, что последний цвет в color_list
должен быть #52BFEC
, что и есть.
Добавление дополнительного кода.
# Begin by converting strings to any number since plt.imshow() needs numbers
float_dict = {
'A': 0.0,
'B': 1.0,
'C': 2.0,
'D': 3.0,
'E': 4.0,
'F': 5.0,
'G': 6.0,
'H': 7.0,
'I': 8.0
}
converted_series = series.map(float_dict).copy()
# Map each float to a specific color
color_dict = {
0.0: '#DA291E',
1.0: '#E7112d',
2.0: '#83CD39',
3.0: '#009934',
4.0: '#007AB3',
5.0: '#54BDEC',
6.0: '#000066',
7.0: '#DDDD11',
8.0: '#572B84',
}
# Create a cmap from a color list
color_list = list(converted_series.map(color_dict))
custom_cmap = ListedColormap(color_list, name="custom_cmap")
# Widen the series into a df
df = series_to_wide_df(converted_series, n_columns=8)
# Plot it
plt.imshow(df, cmap=custom_cmap, interpolation='none')
Результат выше показан на изображении ниже.

- Обратите внимание, что данные на этом изображении не являютсяте же данные в
df
в оригинальном сообщении.
Я тестировал другое color_dict
:
color_dict = {
0.0: '#FF0000',
1.0: '#FF0000',
2.0: '#FF0000',
3.0: '#FF0000',
4.0: '#FF0000',
5.0: '#000000',
6.0: '#000000',
7.0: '#000000',
8.0: '#000000'
}
Но цвета по-прежнему не отображаютсяправильно.С этими цветами 1.0
, 2.0
, 6.0
, 7.0
и некоторые 8.0
получают красный цвет.