英文:
How to fix seaborn heatmap color mapping when values are in wide range
问题
我有一个包含0-9范围内的6个唯一值的数据框架。我想为每个值分配特定的颜色,但映射对我不起作用。
这是我的数据框架的样子:
cmap_new = {0: '#faf5f5', 1: '#ff0303', 6: '#1f78b4', 7: '#b2df8a', 8: '#33a02c', 9: '#fb9a99'}
cmap = ListedColormap([cmap_new[i] for i in cmap_new.keys()])
ax = sns.heatmap(data=tmp_df, cmap=cmap, yticklabels=True, xticklabels=False, linewidths=1, square=True, annot=True)
我的图表看起来像这样:
在我的数据中,尽管我没有值[2-5],它们被分配了一种颜色。我想修复这个问题,只为cmap_new字典中的键分配颜色。
有人可以帮助我吗?
英文:
I have a dataframe with 6 unique values in range(0-9). I want to assign specif color to each value but mapping is not working for me.
This is how my dataframe looks like:
cmap_new = {0: '#faf5f5', 1: '#ff0303', 6: '#1f78b4', 7: '#b2df8a', 8: '#33a02c', 9: '#fb9a99'}
cmap = ListedColormap([cmap_new[i] for i in cmap_new.keys()])
ax = sns.heatmap(data=tmp_df, cmap=cmap, yticklabels=True, xticklabels=False,linewidths=1,square=True,annot=True)
My plot looks like this:
In my data, though I dont have values [2-5], they are assigned a color. I want to fix this problem and assign colors only to keys in the cmap_new dictionary.
Can anyone help me with this?
答案1
得分: 1
你可以使用BoundaryNorm
来为每个数值分配颜色。需要额外的一个值,因为7个边界定义了6个颜色区域。为了获得一个漂亮的颜色条,刻度可以移动到每个区域的中心。
import seaborn as sns
import matplotlib.pyplot as plt
from matplotlib.colors import ListedColormap, BoundaryNorm
import pandas as pd
cmap_new = {0: '#faf5f5', 1: '#ff0303', 6: '#1f78b4', 7: '#b2df8a', 8: '#33a02c', 9: '#fb9a99'}
keys = sorted(cmap_new.keys())
keys += [max(keys) + 1]
tmp_df = pd.DataFrame(np.random.choice(keys, size=(8, 7)),
index=['Zoros', 'Lyra', 'Elara', 'Drakor', 'Astra', 'Mystalin', 'Terra', 'Vora'])
cmap = ListedColormap([cmap_new[k] for k in keys[:-1]])
norm = BoundaryNorm(keys, ncolors=len(keys) - 1)
ax = sns.heatmap(data=tmp_df, cmap=cmap, norm=norm,
yticklabels=True, xticklabels=False, linewidths=1, square=True, annot=True)
ax.collections[0].colorbar.set_ticks([(k1 + k2) / 2 for k1, k2 in zip(keys[:-1], keys[1:])], labels=keys[:-1])
plt.show()
英文:
You can use a BoundaryNorm
to assign a color to each of the values used. An extra value is needed, as 7 boundaries define 6 color regions. In order to get a nice colorbar, the ticks can be moved to the centers of each region.
import seaborn as sns
import matplotlib.pyplot as plt
from matplotlib.colors import ListedColormap, BoundaryNorm
import pandas as pd
cmap_new = {0: '#faf5f5', 1: '#ff0303', 6: '#1f78b4', 7: '#b2df8a', 8: '#33a02c', 9: '#fb9a99'}
keys = sorted(cmap_new.keys())
keys += [max(keys) + 1]
tmp_df = pd.DataFrame(np.random.choice(keys, size=(8, 7)),
index=['Zoros', 'Lyra', 'Elara', 'Drakor', 'Astra', 'Mystalin', 'Terra', 'Vora'])
cmap = ListedColormap([cmap_new[k] for k in keys[:-1]])
norm = BoundaryNorm(keys, ncolors=len(keys) - 1)
ax = sns.heatmap(data=tmp_df, cmap=cmap, norm=norm,
yticklabels=True, xticklabels=False, linewidths=1, square=True, annot=True)
ax.collections[0].colorbar.set_ticks([(k1 + k2) / 2 for k1, k2 in zip(keys[:-1], keys[1:])], labels=keys[:-1])
plt.show()
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论