群的Dendogram染色

2024-09-30 18:12:33 发布

您现在位置:Python中文网/ 问答频道 /正文

我使用seaborn clustermap基于spearman的相关矩阵创建了一个heatmap,如下所示:我想绘制树状图。我希望树状图像这样: dendrogram 但是在热图上

我创建了一个颜色目录,如下所示,但出现了一个错误:

def assign_tree_colour(name,val_dict,coding_names_df):
ret = None
if val_dict.get(name, '') == 'Group 1':
    ret = "(0,0.9,0.4)"   #green
elif val_dict.get(name, '') == 'Group 2':
    ret = "(0.6,0.1,0)"   #red
elif val_dict.get(name, '') == 'Group 3':
    ret = "(0.3,0.8,1)"   #light blue
elif val_dict.get(name, '') == 'Group 4':
    ret = "(0.4,0.1,1)"   #purple
elif val_dict.get(name, '') == 'Group 5':
    ret = "(1,0.9,0.1)"   #yellow
elif val_dict.get(name, '') == 'Group 6':
    ret = "(0,0,0)"   #black
else:
    ret = "(0,0,0)"         #black
return ret

def fix_string(str):
    return str.replace('"', '')

external_data3 = [list(z) for z in coding_names_df.values]
external_data3 = {fix_string(z[0]): z[3] for z in external_data3}

tree_label = list(df.index)
tree_label = [fix_string(x) for x in tree_label]
tree_labels = { j : tree_label[j] for j in range(0, len(tree_label) ) }

tree_colour = [assign_tree_colour(label, external_data3, coding_names_df) for label in tree_labels]
tree_colors = { i : tree_colour[i] for i in range(0, len(tree_colour) ) }


sns.set(color_codes=True)
sns.set(font_scale=1)
g = sns.clustermap(df, cmap="bwr",
                   vmin=-1, vmax=1,
                   yticklabels=1, xticklabels=1,
                   cbar_kws={"ticks":[-1,-0.5,0,0.5,1]},
                   figsize=(13,13),
                   row_colors=row_colors,
                   col_colors=col_colors,
                   method='average',
                   metric='correlation',
                   tree_kws=dict(colors=tree_colors))
g.ax_heatmap.set_xlabel('Genus')
g.ax_heatmap.set_ylabel('Genus')
for label in Group.unique():
    g.ax_col_dendrogram.bar(0, 0, color=lut[label],
                            label=label, linewidth=0)
g.ax_col_dendrogram.legend(loc=9, ncol=7, bbox_to_anchor=(0.26, 0., 0.5, 1.5))
ax=g.ax_heatmap



 File "<ipython-input-64-4bc6be89afe3>", line 11, in <module>
tree_kws=dict(colors=tree_colors))



File "C:\Users\rotemb\AppData\Local\Continuum\anaconda3\lib\site-packages\seaborn\matrix.py", line 1391, in clustermap
    tree_kws=tree_kws, **kwargs)

  File "C:\Users\rotemb\AppData\Local\Continuum\anaconda3\lib\site-packages\seaborn\matrix.py", line 1208, in plot
    tree_kws=tree_kws)

  File "C:\Users\rotemb\AppData\Local\Continuum\anaconda3\lib\site-packages\seaborn\matrix.py", line 1054, in plot_dendrograms
    tree_kws=tree_kws

  File "C:\Users\rotemb\AppData\Local\Continuum\anaconda3\lib\site-packages\seaborn\matrix.py", line 776, in dendrogram
    return plotter.plot(ax=ax, tree_kws=tree_kws)

  File "C:\Users\rotemb\AppData\Local\Continuum\anaconda3\lib\site-packages\seaborn\matrix.py", line 692, in plot
    **tree_kws)

  File "C:\Users\rotemb\AppData\Local\Continuum\anaconda3\lib\site-packages\matplotlib\collections.py", line 1316, in __init__
    colors = mcolors.to_rgba_array(colors)

  File "C:\Users\rotemb\AppData\Local\Continuum\anaconda3\lib\site-packages\matplotlib\colors.py", line 294, in to_rgba_array
    result[i] = to_rgba(cc, alpha)

  File "C:\Users\rotemb\AppData\Local\Continuum\anaconda3\lib\site-packages\matplotlib\colors.py", line 177, in to_rgba
    rgba = _to_rgba_no_colorcycle(c, alpha)

  File "C:\Users\rotemb\AppData\Local\Continuum\anaconda3\lib\site-packages\matplotlib\colors.py", line 240, in _to_rgba_no_colorcycle
    raise ValueError("Invalid RGBA argument: {!r}".format(orig_c))

ValueError: Invalid RGBA argument: 0

在此方面的任何帮助都将不胜感激! Tnx


Tags: intreelocallineusersappdatalabeldict
2条回答

基于上述答案,下面是一个以不同方式为主要三个分支着色的示例,暴力(前49行为红色,后35行为绿色,最后62行为蓝色,其余两行为黑色):

import matplotlib.pyplot as plt
import seaborn as sns; sns.set(color_codes=True)
import pandas as pd


iris = sns.load_dataset("iris")
species = iris.pop("species")
g = sns.clustermap(iris)
lut = dict(zip(species.unique(), "rbg"))
row_colors = species.map(lut)
# For demonstrating the hierarchical sidebar coloring
df_colors = pd.DataFrame(data={'r': row_colors[row_colors == 'r'], 'g': row_colors[row_colors == 'g'], 'b': row_colors[row_colors == 'b']}) 
# Simple class RGBA colormap
colmap = {'setosa': (1, 0, 0, 0.7), 'virginica': (0, 1, 0, 0.7), 'versicolor': (0, 0, 1, 0.7)}
g = sns.clustermap(iris, row_colors=df_colors, tree_kws={'colors':[(1,0,0,1)]*49+[(0,1,0,1)]*35+[(0,0,1,1)]*63+[(0,0,0,1)]*2})
plt.savefig('clustermap.png')

Brute Force coloring

对于一般情况,可从树状图(此处描述scipy linkage format)中得出要着色的线条数:

n_leaves = len(g.dendrogram_row.linkage)+1
n0_ndx = len(g.dendrogram_row.linkage) - 1
n1_ndx = int(g.dendrogram_row.linkage[n0_ndx][0])-n_leaves
n2_ndx = int(g.dendrogram_row.linkage[n0_ndx][1])-n_leaves
n21_ndx = int(g.dendrogram_row.linkage[n2_ndx][0])-n_leaves
n22_ndx = int(g.dendrogram_row.linkage[n2_ndx][1])-n_leaves

n1 = int(g.dendrogram_row.linkage[n1_ndx][3])-1
n21 = int(g.dendrogram_row.linkage[n21_ndx][3])-1
n22 = int(g.dendrogram_row.linkage[n22_ndx][3])-1

g = sns.clustermap(iris, row_colors=df_colors, tree_kws={'colors':[(1,0,0,1)]*n1+[(0,1,0,1)]*n21+[(0,0,1,1)]*n22+[(0,0,0,1)]*(n_leave\
s-1-n1-n21-n22)})

尽管如此,我还没有找到一种方法来改变顶部树状图的颜色

根据^{}文档,可以通过tree_kws(采用dict)及其colors属性设置树状图着色,该属性需要一个RGB元组列表,如(0.5, 0.5, 1)。似乎colors除了RGB元组格式的数据外,什么都不支持

您是否注意到clustermap支持树状图和相关矩阵之间的层次颜色条的嵌套列表或数据帧?如果树状图过于拥挤,它们可能会很有用

我希望这有帮助

编辑

RGB列表是LineCollection中线条颜色的序列——它使用序列在两个树状图中绘制每条线条。(顺序似乎从列树状图的最右侧分支开始)为了将某个标签与数据点关联,需要计算树状图中数据点的绘图顺序

编辑二

下面是一个基于^{}示例为树着色的最小示例:

import matplotlib.pyplot as plt
import seaborn as sns; sns.set(color_codes=True)
import pandas as pd


iris = sns.load_dataset("iris")
species = iris.pop("species")
g = sns.clustermap(iris)
lut = dict(zip(species.unique(), "rbg"))
row_colors = species.map(lut)
# For demonstrating the hierarchical sidebar coloring
df_colors = pd.DataFrame(data={'r': row_colors[row_colors == 'r'], 'g': row_colors[row_colors == 'g'], 'b': row_colors[row_colors == 'b']}) 
# Simple class RGBA colormap
colmap = {'setosa': (1, 0, 0, 0.7), 'virginica': (0, 1, 0, 0.7), 'versicolor': (0, 0, 1, 0.7)}
g = sns.clustermap(iris, row_colors=df_colors, tree_kws={'colors':[colmap[s] for s in species]})
plt.savefig('clustermap.png')

clustermap.png 如您所见,树的绘制线顺序从图像的右上角开始,因此不会与clustermap中显示的数据点顺序相关联。另一方面,颜色条(由{row,col}_colors属性控制)可用于此目的

相关问题 更多 >