Plotten des Konzentrations-Priors

Machine LearningMachine LearningBeginner
Jetzt üben

This tutorial is from open-source community. Access the source code

💡 Dieser Artikel wurde von AI-Assistenten übersetzt. Um die englische Version anzuzeigen, können Sie hier klicken

Einführung

In diesem Lab wird gezeigt, wie die Klasse BayesianGaussianMixture aus scikit-learn verwendet wird, um einem Toy-Datensatz anzupassen, der eine Mischung von drei Gaußverteilungen enthält. Die Klasse kann automatisch die Anzahl der Mischungskomponenten anpassen, indem sie einen Konzentrations-Prior verwendet, der über das Parameter weight_concentration_prior_type angegeben wird. In diesem Lab wird der Unterschied zwischen der Verwendung eines Dirichlet-Verteilungs-Priors und eines Dirichlet-Prozess-Priors gezeigt, um die Anzahl der Komponenten mit nicht-null Gewichten zu wählen.

Tipps für die VM

Nachdem der VM-Start abgeschlossen ist, klicken Sie in der oberen linken Ecke, um zur Registerkarte Notebook zu wechseln und Jupyter Notebook für die Übung zu nutzen.

Manchmal müssen Sie einige Sekunden warten, bis Jupyter Notebook vollständig geladen ist. Die Validierung von Vorgängen kann aufgrund von Einschränkungen in Jupyter Notebook nicht automatisiert werden.

Wenn Sie während des Lernens Probleme haben, können Sie Labby gerne fragen. Geben Sie nach der Sitzung Feedback, und wir werden das Problem für Sie prompt beheben.

Bibliotheken importieren

In diesem Schritt importieren wir die erforderlichen Bibliotheken, nämlich numpy, matplotlib, gridspec und BayesianGaussianMixture aus sklearn.mixture.

import numpy as np
import matplotlib.pyplot as plt
import matplotlib.gridspec as gridspec
from sklearn.mixture import BayesianGaussianMixture

Funktionen definieren

In diesem Schritt definieren wir zwei Funktionen. Die erste Funktion zeigt Ellipsen an, die aus dem Toy-Datensatz stammen, der von den Modellen der Klasse BayesianGaussianMixture angepasst wurde. Die zweite Funktion zeigt die Ergebnisse für drei verschiedene Werte des Gewichts-Konzentrations-Priors an.

def plot_ellipses(ax, weights, means, covars):
    for n in range(means.shape[0]):
        eig_vals, eig_vecs = np.linalg.eigh(covars[n])
        unit_eig_vec = eig_vecs[0] / np.linalg.norm(eig_vecs[0])
        angle = np.arctan2(unit_eig_vec[1], unit_eig_vec[0])
        angle = 180 * angle / np.pi
        eig_vals = 2 * np.sqrt(2) * np.sqrt(eig_vals)
        ell = mpl.patches.Ellipse(
            means[n], eig_vals[0], eig_vals[1], angle=180 + angle, edgecolor="black"
        )
        ell.set_clip_box(ax.bbox)
        ell.set_alpha(weights[n])
        ell.set_facecolor("#56B4E9")
        ax.add_artist(ell)

def plot_results(ax1, ax2, estimator, X, y, title, plot_title=False):
    ax1.set_title(title)
    ax1.scatter(X[:, 0], X[:, 1], s=5, marker="o", color=colors[y], alpha=0.8)
    ax1.set_xlim(-2.0, 2.0)
    ax1.set_ylim(-3.0, 3.0)
    ax1.set_xticks(())
    ax1.set_yticks(())
    plot_ellipses(ax1, estimator.weights_, estimator.means_, estimator.covariances_)

    ax2.get_xaxis().set_tick_params(direction="out")
    ax2.yaxis.grid(True, alpha=0.7)
    for k, w in enumerate(estimator.weights_):
        ax2.bar(
            k,
            w,
            width=0.9,
            color="#56B4E9",
            zorder=3,
            align="center",
            edgecolor="black",
        )
        ax2.text(k, w + 0.007, "%.1f%%" % (w * 100.0), horizontalalignment="center")
    ax2.set_xlim(-0.6, 2 * n_components - 0.4)
    ax2.set_ylim(0.0, 1.1)
    ax2.tick_params(axis="y", which="both", left=False, right=False, labelleft=False)
    ax2.tick_params(axis="x", which="both", top=False)
    if plot_title:
        ax1.set_ylabel("Estimated Mixtures")
        ax2.set_ylabel("Weight of each component")

Parameter für den Toy-Datensatz festlegen

In diesem Schritt legen wir die Parameter für den Toy-Datensatz fest, die die Zufallszahl, die Anzahl der Komponenten, die Anzahl der Merkmale, die Farben, die Kovarianzen, die Stichproben und die Mittelwerte umfassen.

random_state, n_components, n_features = 2, 3, 2
colors = np.array(["#0072B2", "#F0E442", "#D55E00"])
covars = np.array(
    [[[0.7, 0.0], [0.0, 0.1]], [[0.5, 0.0], [0.0, 0.1]], [[0.5, 0.0], [0.0, 0.1]]]
)
samples = np.array([200, 500, 200])
means = np.array([[0.0, -0.70], [0.0, 0.0], [0.0, 0.70]])

Schätzer definieren

In diesem Schritt definieren wir zwei Schätzer. Der erste Schätzer verwendet einen Dirichlet-Verteilungs-Prior, um die Anzahl der Komponenten mit nicht-null Gewichten festzulegen. Der zweite Schätzer verwendet einen Dirichlet-Prozess-Prior, um die Anzahl der Komponenten auszuwählen.

estimators = [
    (
        "Finite mixture with a Dirichlet distribution\nprior and " r"$\gamma_0=$",
        BayesianGaussianMixture(
            weight_concentration_prior_type="dirichlet_distribution",
            n_components=2 * n_components,
            reg_covar=0,
            init_params="random",
            max_iter=1500,
            mean_precision_prior=0.8,
            random_state=random_state,
        ),
        [0.001, 1, 1000],
    ),
    (
        "Infinite mixture with a Dirichlet process\n prior and" r"$\gamma_0=$",
        BayesianGaussianMixture(
            weight_concentration_prior_type="dirichlet_process",
            n_components=2 * n_components,
            reg_covar=0,
            init_params="random",
            max_iter=1500,
            mean_precision_prior=0.8,
            random_state=random_state,
        ),
        [1, 1000, 100000],
    ),
]

Daten generieren

In diesem Schritt generieren wir Daten mit der Funktion numpy.random.RandomState und den in Schritt 3 definierten Parametern.

rng = np.random.RandomState(random_state)
X = np.vstack(
    [
        rng.multivariate_normal(means[j], covars[j], samples[j])
        for j in range(n_components)
    ]
)
y = np.concatenate([np.full(samples[j], j, dtype=int) for j in range(n_components)])

Ergebnisse plotten

In diesem Schritt plotten wir die Ergebnisse für jeden Schätzer mit der in Schritt 2 definierten Funktion plot_results.

for title, estimator, concentrations_prior in estimators:
    plt.figure(figsize=(4.7 * 3, 8))
    plt.subplots_adjust(
        bottom=0.04, top=0.90, hspace=0.05, wspace=0.05, left=0.03, right=0.99
    )

    gs = gridspec.GridSpec(3, len(concentrations_prior))
    for k, concentration in enumerate(concentrations_prior):
        estimator.weight_concentration_prior = concentration
        estimator.fit(X)
        plot_results(
            plt.subplot(gs[0:2, k]),
            plt.subplot(gs[2, k]),
            estimator,
            X,
            y,
            r"%s$%.1e$" % (title, concentration),
            plot_title=k == 0,
        )

plt.show()

Zusammenfassung

In diesem Lab wurde gezeigt, wie die Klasse BayesianGaussianMixture aus scikit-learn verwendet werden kann, um einen Toy-Datensatz anzupassen, der aus einer Mischung von drei Gaußverteilungen besteht. Die Klasse kann automatisch die Anzahl ihrer Mischkomponenten anpassen, indem ein Konzentrations-Prior verwendet wird, der über das Parameter weight_concentration_prior_type angegeben wird. In diesem Lab wurde der Unterschied zwischen der Verwendung eines Dirichlet-Verteilungs-Priors und eines Dirichlet-Prozess-Priors gezeigt, um die Anzahl der Komponenten mit nicht-null Gewichten auszuwählen.