Get clusters from dendrogram python

I have a list of words on which I performed TF-IDF Algorithm to get the list of top 100 words. After which I am supposed to perform clustering. For now I am able to do both of the tasks (I am sharing relevant part of the code and input file, screenshot of output).

My Query is that I wanted the list of the clusters that are formed in the output Dendrogram, How can I do that? The Dendrogram function returns a Tuple ax which has some co ordinates and list of the nodes. How can I manipulate them to get the complete list of Clusters.

The following is extract from the input file.

"recommended stories dylan scott stat advertisement kate sheridan dylan scott dylan scott",
"email touting former representative mike fergusons genuine connection",
"email touting former representative mike ferguson \u2019",
"facebook donald trump fda hhs privacy policy",
"president trump appoints dr scott gottlieb",
"trade groups including novartis ag",
"bush alumni coalition supporting trump",
"online presidential transition analysis center",
"tennessee republican representative marsha blackburn",
"nonprofit global health care company",
"paula stannard ,\u201d said ladd wiley",
"bremberg returned calls seeking comment",
"0 \u2026. 0 \u2026 1c",
"2016 w ashington \u2014 let",
"take place ,\u201d said dr",
"\u201c selling baby parts .\u201d",
"health care companies whose boards",
"transition ,\u201d said lisa tofil",

The following is the code that I am using

punctuations = '''!()-[]{};:'\<>./?@#$%^&*_~'''
n_a =fin_a= ""
for file in os.listdir():
    if (file.endswith(".kwp")):
        with open(file) as f:
            #print(f.read())
            a = f.read()
            a = re.sub(r"\\[a-z0-9A-Z]+","",a)
            a = re.sub(r"\"","",a)
            a = re.sub(r"\,","",a)
            #a = re.sub("\\","",a)
            #print(a)
            for ch in a:
                if (ch not in punctuations):
                    n_a = n_a + ch
            n_a = n_a.lower()
            #print(n_a)
            #new_f = open("n")

        fin_a = fin_a + n_a 

tfidf_vectorizer = TfidfVectorizer(max_df=1,stop_words='english',use_idf=True)
tfd_mat = tfidf_vectorizer.fit_transform([n_a])
dense = tfd_mat.todense()
#print(len(dense[0].tolist()[0]))
ep = dense[0].tolist()[0]
phrase_scores = [pair for pair in zip(range(0, len(ep)), ep) if pair[1] > 0]
#print(phrase_scores)
#print(len(phrase_scores))
phrase_scores=sorted(phrase_scores, key=lambda t: t[1] * -1)[:100]
#rint(tfd_mat)
fin_term = []
terms = tfidf_vectorizer.get_feature_names()
with open("/home/laitkor/Desktop/New_Paul/kwp_top100.txt","w") as fl:
    for t in range(0,100):
        #print(t)
        key,valu = phrase_scores[t]
        #print(key)
        #print(valu)
        fl.write(terms[key]+'\n')
        fin_term.append(terms[key])
#print(fin_term)    
#print(phrase_scores[1:100])
dist = 1 - cosine_similarity(phrase_scores[1:100])
#print(dist)
linkage_matrix = ward(dist)
#print(linkage_matrix)
fig, ax = plt.subplots(figsize=(30, 30)) # set size
ax = dendrogram(linkage_matrix, orientation="right", labels=fin_term);
#print(ax)
#print(leaves)
plt.tick_params(\
    axis= 'x',          # changes apply to the x-axis
    which='both',      # both major and minor ticks are affected
    bottom='off',      # ticks along the bottom edge are off
    top='off',         # ticks along the top edge are off
    labelbottom='off')

plt.tight_layout() #show plot with tight layout

#uncomment below to save figure
plt.savefig('kw[enter image description here][1]p.png', dpi=200)

The below link contains the output of the Dendrogram formed

https://www.screencast.com/t/2MEc3ohBe

scipy.cluster.hierarchy.dendrogram(Z, p=30, truncate_mode=None, color_threshold=None, get_leaves=True, orientation='top', labels=None, count_sort=False, distance_sort=False, show_leaf_counts=True, no_plot=False, no_labels=False, leaf_font_size=None, leaf_rotation=None, leaf_label_func=None, show_contracted=False, link_color_func=None, ax=None, above_threshold_color='C0')[source]#

Plot the hierarchical clustering as a dendrogram.

The dendrogram illustrates how each cluster is composed by drawing a U-shaped link between a non-singleton cluster and its children. The top of the U-link indicates a cluster merge. The two legs of the U-link indicate which clusters were merged. The length of the two legs of the U-link represents the distance between the child clusters. It is also the cophenetic distance between original observations in the two children clusters.

Parameters Zndarray

The linkage matrix encoding the hierarchical clustering to render as a dendrogram. See the linkage function for more information on the format of Z.

pint, optional

The p parameter for truncate_mode.

truncate_modestr, optional

The dendrogram can be hard to read when the original observation matrix from which the linkage is derived is large. Truncation is used to condense the dendrogram. There are several modes:

None

No truncation is performed (default). Note: 'none' is an alias for None that’s kept for backward compatibility.

'lastp'

The last p non-singleton clusters formed in the linkage are the only non-leaf nodes in the linkage; they correspond to rows Z[n-p-2:end] in Z. All other non-singleton clusters are contracted into leaf nodes.

'level'

No more than p levels of the dendrogram tree are displayed. A “level” includes all nodes with p merges from the final merge.

Note: 'mtica' is an alias for 'level' that’s kept for backward compatibility.

color_thresholddouble, optional

For brevity, let \(t\) be the color_threshold. Colors all the descendent links below a cluster node \(k\) the same color if \(k\) is the first node below the cut threshold \(t\). All links connecting nodes with distances greater than or equal to the threshold are colored with de default matplotlib color 'C0'. If \(t\) is less than or equal to zero, all nodes are colored 'C0'. If color_threshold is None or ‘default’, corresponding with MATLAB(TM) behavior, the threshold is set to 0.7*max(Z[:,2]).

get_leavesbool, optional

Includes a list R['leaves']=H in the result dictionary. For each \(i\), H[i] == j, cluster node j appears in position i in the left-to-right traversal of the leaves, where \(j < 2n-1\) and \(i < n\).

orientationstr, optional

The direction to plot the dendrogram, which can be any of the following strings:

'top'

Plots the root at the top, and plot descendent links going downwards. (default).

'bottom'

Plots the root at the bottom, and plot descendent links going upwards.

'left'

Plots the root at the left, and plot descendent links going right.

'right'

Plots the root at the right, and plot descendent links going left.

labelsndarray, optional

By default, labels is None so the index of the original observation is used to label the leaf nodes. Otherwise, this is an \(n\)-sized sequence, with n == Z.shape[0] + 1. The labels[i] value is the text to put under the \(i\) th leaf node only if it corresponds to an original observation and not a non-singleton cluster.

count_sortstr or bool, optional

For each node n, the order (visually, from left-to-right) n’s two descendent links are plotted is determined by this parameter, which can be any of the following values:

False

Nothing is done.

'ascending' or True

The child with the minimum number of original objects in its cluster is plotted first.

'descending'

The child with the maximum number of original objects in its cluster is plotted first.

Note, distance_sort and count_sort cannot both be True.

distance_sortstr or bool, optional

For each node n, the order (visually, from left-to-right) n’s two descendent links are plotted is determined by this parameter, which can be any of the following values:

False

Nothing is done.

'ascending' or True

The child with the minimum distance between its direct descendents is plotted first.

'descending'

The child with the maximum distance between its direct descendents is plotted first.

Note distance_sort and count_sort cannot both be True.

show_leaf_countsbool, optional

When True, leaf nodes representing \(k>1\) original observation are labeled with the number of observations they contain in parentheses.

no_plotbool, optional

When True, the final rendering is not performed. This is useful if only the data structures computed for the rendering are needed or if matplotlib is not available.

no_labelsbool, optional

When True, no labels appear next to the leaf nodes in the rendering of the dendrogram.

leaf_rotationdouble, optional

Specifies the angle (in degrees) to rotate the leaf labels. When unspecified, the rotation is based on the number of nodes in the dendrogram (default is 0).

leaf_font_sizeint, optional

Specifies the font size (in points) of the leaf labels. When unspecified, the size based on the number of nodes in the dendrogram.

leaf_label_funclambda or function, optional

When leaf_label_func is a callable function, for each leaf with cluster index \(k < 2n-1\). The function is expected to return a string with the label for the leaf.

Indices \(k < n\) correspond to original observations while indices \(k \geq n\) correspond to non-singleton clusters.

For example, to label singletons with their node id and non-singletons with their id, count, and inconsistency coefficient, simply do:

# First define the leaf label function.
def llf(id):
    if id < n:
        return str(id)
    else:
        return '[%d %d %1.2f]' % (id, count, R[n-id,3])

# The text for the leaf nodes is going to be big so force
# a rotation of 90 degrees.
dendrogram(Z, leaf_label_func=llf, leaf_rotation=90)

# leaf_label_func can also be used together with ``truncate_mode`` parameter,
# in which case you will get your leaves labeled after truncation:
dendrogram(Z, leaf_label_func=llf, leaf_rotation=90,
           truncate_mode='level', p=2)

show_contractedbool, optional

When True the heights of non-singleton nodes contracted into a leaf node are plotted as crosses along the link connecting that leaf node. This really is only useful when truncation is used (see truncate_mode parameter).

link_color_funccallable, optional

If given, link_color_function is called with each non-singleton id corresponding to each U-shaped link it will paint. The function is expected to return the color to paint the link, encoded as a matplotlib color string code. For example:

dendrogram(Z, link_color_func=lambda k: colors[k])

colors the direct links below each untruncated non-singleton node k using colors[k].

axmatplotlib Axes instance, optional

If None and no_plot is not True, the dendrogram will be plotted on the current axes. Otherwise if no_plot is not True the dendrogram will be plotted on the given Axes instance. This can be useful if the dendrogram is part of a more complex figure.

above_threshold_colorstr, optional

This matplotlib color string sets the color of the links above the color_threshold. The default is 'C0'.

Returns Rdict

A dictionary of data structures computed to render the dendrogram. Its has the following keys:

'color_list'

A list of color names. The k’th element represents the color of the k’th link.

'icoord' and 'dcoord'

Each of them is a list of lists. Let icoord = [I1, I2, ..., Ip] where Ik = [xk1, xk2, xk3, xk4] and dcoord = [D1, D2, ..., Dp] where Dk = [yk1, yk2, yk3, yk4], then the k’th link painted is (xk1, yk1) - (xk2, yk2) - (xk3, yk3) - (xk4, yk4).

'ivl'

A list of labels corresponding to the leaf nodes.

'leaves'

For each i, H[i] == j, cluster node j appears in position i in the left-to-right traversal of the leaves, where \(j < 2n-1\) and \(i < n\). If j is less than n, the i-th leaf node corresponds to an original observation. Otherwise, it corresponds to a non-singleton cluster.

'leaves_color_list'

A list of color names. The k’th element represents the color of the k’th leaf.

Notes

It is expected that the distances in Z[:,2] be monotonic, otherwise crossings appear in the dendrogram.

Examples

>>> from scipy.cluster import hierarchy
>>> import matplotlib.pyplot as plt

A very basic example:

>>> ytdist = np.array([662., 877., 255., 412., 996., 295., 468., 268.,
...                    400., 754., 564., 138., 219., 869., 669.])
>>> Z = hierarchy.linkage(ytdist, 'single')
>>> plt.figure()
>>> dn = hierarchy.dendrogram(Z)

Now, plot in given axes, improve the color scheme and use both vertical and horizontal orientations:

>>> hierarchy.set_link_color_palette(['m', 'c', 'y', 'k'])
>>> fig, axes = plt.subplots(1, 2, figsize=(8, 3))
>>> dn1 = hierarchy.dendrogram(Z, ax=axes[0], above_threshold_color='y',
...                            orientation='top')
>>> dn2 = hierarchy.dendrogram(Z, ax=axes[1],
...                            above_threshold_color='#bcbddc',
...                            orientation='right')
>>> hierarchy.set_link_color_palette(None)  # reset to default after use
>>> plt.show()

Get clusters from dendrogram python
Get clusters from dendrogram python

How do you find the number of clusters in a dendrogram Python?

In the dendrogram locate the largest vertical difference between nodes, and in the middle pass an horizontal line. The number of vertical lines intersecting it is the optimal number of clusters (when affinity is calculated using the method set in linkage).

How many clusters do we get from dendrogram?

Looking at this dendrogram, you can see the three clusters as three branches that occur at about the same horizontal distance. The two outliers, 6 and 13, are fused in rather arbitrarily at much higher distances. This is the interpretation.

How do I display a dendrogram in Python?

Dendrograms in Python.
Basic Dendrogram. A dendrogram is a diagram representing a tree. The figure factory called create_dendrogram performs hierarchical clustering on data and represents the resulting tree. ... .
Set Color Threshold..
Set Orientation and Add Labels..
Plot a Dendrogram with a Heatmap. See also the Dash Bio demo..