{ "cells": [ { "cell_type": "markdown", "metadata": {}, "source": [ "# Uniform Manifold Approximation and Projection (UMAP)\n", "UMAP is a dimensionality reduction algorithm which performs non-linear dimension reduction. It can also be used for visualization of the dataset. The UMAP model implemented in cuml allows the user to set the following parameter values:\n", "1.\tn_neighbors: number of neighboring samples used for manifold approximation. Larger values result in more global views of the manifold, while smaller values result in more local data being preserved (default = 15)\n", "2.\tn_components: the dimension of the space to embed into (default = 2)\n", "3.\tn_epochs: number of training epochs to be used in optimizing the low dimensional embedding (default = None)\n", "4.\tlearning_rate: initial learning rate for the embedding optimization (default = 1.0)\n", "5.\tinit: the low dimensional embedding to use: a. 'spectral': use a spectral embedding of the fuzzy 1-skeleton b. 'random': assign initial embedding positions at random (default = 'spectral')\n", "6.\tmin_dist: the minimum distance that should be present between embedded points (default = 0.1)\n", "7.\tspread: determines how clustered the embedded points will be (default = 1.0)\n", "8.\tset_op_mix_ratio: is the ratio of pure fuzzy union to intersection. If the value is 1.0 then it will be a pure fuzzy union and for the value of 0.0 it will be a pure fuzzy interpolation (default = 1.0)\n", "9.\tlocal_connectivity: number of nearest neighbors that should be assumed to be connected at a local level. It should be not more than the local intrinsic dimension of the manifold (default = 1)\n", "10.\trepulsion_strength: weighting applied to negative samples in low dimensional embedding optimization. Values > 1 implements a higher negative value to the samples (default = 1.0)\n", "11.\tnegative_sample_rate: the rate at which the negative samples should be selected per positive sample during the optimization process (default = 5)\n", "12.\ttransform_queue_size: embedding new points using a trained model_ will control how aggressively to search for nearest neighbors (default = 4.0)\n", "13.\tverbose: bool (default False)\n", "\n", "The cuml implemetation of the UMAP model has the following functions that one can run:\n", "1.\tfit: it fits the dataset into an embedded space\n", "2.\tfit_transform: it fits the dataset into an embedded space and returns the transformed output\n", "3.\ttransform: it transforms the dataset into an existing embedded space and returns the low dimensional output\n", "\n", "The model can take array-like objects, either in host as NumPy arrays or in device (as Numba or _cuda_array_interface_compliant), as well as cuDF DataFrames. In order to convert your dataset to cudf format please read the cudf documentation on https://rapidsai.github.io/projects/cudf/en/latest/. For additional information on the UMAP model please refer to the documentation on https://rapidsai.github.io/projects/cuml/en/0.6.0/api.html#cuml.UMAP" ] }, { "cell_type": "code", "execution_count": 1, "metadata": {}, "outputs": [], "source": [ "import numpy as np\n", "import pandas as pd\n", "\n", "import cudf\n", "import os\n", "\n", "from sklearn import datasets\n", "from sklearn.metrics import adjusted_rand_score\n", "from sklearn.cluster import KMeans\n", "from sklearn.manifold.t_sne import trustworthiness\n", "\n", "from cuml.manifold.umap import UMAP" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "# Running cuml's UMAP model on blobs dataset" ] }, { "cell_type": "code", "execution_count": 12, "metadata": {}, "outputs": [], "source": [ "# create a blobs dataset with 500 samples and 10 features each\n", "data, labels = datasets.make_blobs(\n", " n_samples=500, n_features=10, centers=5)" ] }, { "cell_type": "code", "execution_count": 13, "metadata": {}, "outputs": [], "source": [ "# using the cuml UMAP algorithm to reduce the features of the dataset and store\n", "embedding = UMAP().fit_transform(data)" ] }, { "cell_type": "code", "execution_count": 14, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "1.0\n" ] } ], "source": [ "# calculate the score of the results obtained using cuml's algorithm and sklearn kmeans\n", "score = adjusted_rand_score(labels,\n", " KMeans(5).fit_predict(embedding))\n", "print(score) # should equal 1.0" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "# Running cuml's UMAP model on iris dataset" ] }, { "cell_type": "code", "execution_count": 15, "metadata": {}, "outputs": [], "source": [ "# load the iris dataset from sklearn and extract the required information\n", "iris = datasets.load_iris()\n", "data = iris.data" ] }, { "cell_type": "code", "execution_count": 16, "metadata": { "scrolled": true }, "outputs": [], "source": [ "# define the cuml UMAP model and use fit_transform function to obtain the low dimensional output of the input dataset\n", "embedding = UMAP(\n", " n_neighbors=10, min_dist=0.01, init=\"random\"\n", ").fit_transform(data)" ] }, { "cell_type": "code", "execution_count": 17, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "0.9741363073110285\n" ] } ], "source": [ "# calculate the trust worthiness of the results obtaind from the cuml UMAP\n", "trust = trustworthiness(iris.data, embedding, 10)\n", "print(trust)" ] }, { "cell_type": "code", "execution_count": 18, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "[[5.1 3.5 1.4 0.2]\n", " [4.9 3. 1.4 0.2]\n", " [4.6 3.1 1.5 0.2]\n", " [5. 3.6 1.4 0.2]\n", " [4.6 3.4 1.4 0.3]\n", " [5. 3.4 1.5 0.2]\n", " [4.4 2.9 1.4 0.2]\n", " [4.9 3.1 1.5 0.1]\n", " [5.4 3.7 1.5 0.2]\n", " [4.8 3.4 1.6 0.2]\n", " [4.8 3. 1.4 0.1]\n", " [4.3 3. 1.1 0.1]\n", " [5.7 4.4 1.5 0.4]\n", " [5.4 3.9 1.3 0.4]\n", " [5.1 3.5 1.4 0.3]\n", " [5.7 3.8 1.7 0.3]\n", " [5.1 3.8 1.5 0.3]\n", " [5.4 3.4 1.7 0.2]\n", " [5.1 3.3 1.7 0.5]\n", " [4.8 3.4 1.9 0.2]\n", " [5. 3. 1.6 0.2]\n", " [5. 3.4 1.6 0.4]\n", " [5.2 3.4 1.4 0.2]\n", " [4.7 3.2 1.6 0.2]\n", " [4.8 3.1 1.6 0.2]\n", " [5.2 4.1 1.5 0.1]\n", " [5.5 4.2 1.4 0.2]\n", " [5. 3.2 1.2 0.2]\n", " [4.9 3.6 1.4 0.1]\n", " [4.4 3. 1.3 0.2]\n", " [5. 3.5 1.3 0.3]\n", " [4.5 2.3 1.3 0.3]\n", " [4.4 3.2 1.3 0.2]\n", " [5. 3.5 1.6 0.6]\n", " [5.1 3.8 1.9 0.4]\n", " [4.8 3. 1.4 0.3]\n", " [5.1 3.8 1.6 0.2]\n", " [4.6 3.2 1.4 0.2]\n", " [5.3 3.7 1.5 0.2]\n", " [5. 3.3 1.4 0.2]\n", " [7. 3.2 4.7 1.4]\n", " [6.4 3.2 4.5 1.5]\n", " [6.9 3.1 4.9 1.5]\n", " [5.5 2.3 4. 1.3]\n", " [6.5 2.8 4.6 1.5]\n", " [5.7 2.8 4.5 1.3]\n", " [6.3 3.3 4.7 1.6]\n", " [4.9 2.4 3.3 1. ]\n", " [6.6 2.9 4.6 1.3]\n", " [5.2 2.7 3.9 1.4]\n", " [5. 2. 3.5 1. ]\n", " [5.9 3. 4.2 1.5]\n", " [6.1 2.9 4.7 1.4]\n", " [5.6 2.9 3.6 1.3]\n", " [6.7 3.1 4.4 1.4]\n", " [5.6 3. 4.5 1.5]\n", " [5.8 2.7 4.1 1. ]\n", " [6.2 2.2 4.5 1.5]\n", " [5.9 3.2 4.8 1.8]\n", " [6.1 2.8 4. 1.3]\n", " [6.3 2.5 4.9 1.5]\n", " [6.1 2.8 4.7 1.2]\n", " [6.4 2.9 4.3 1.3]\n", " [6.6 3. 4.4 1.4]\n", " [6.8 2.8 4.8 1.4]\n", " [6. 2.9 4.5 1.5]\n", " [5.7 2.6 3.5 1. ]\n", " [5.5 2.4 3.8 1.1]\n", " [5.5 2.4 3.7 1. ]\n", " [6. 2.7 5.1 1.6]\n", " [5.4 3. 4.5 1.5]\n", " [6.7 3.1 4.7 1.5]\n", " [6.3 2.3 4.4 1.3]\n", " [5.6 3. 4.1 1.3]\n", " [5.5 2.5 4. 1.3]\n", " [6.1 3. 4.6 1.4]\n", " [5.8 2.6 4. 1.2]\n", " [5. 2.3 3.3 1. ]\n", " [5.6 2.7 4.2 1.3]\n", " [5.7 3. 4.2 1.2]\n", " [6.2 2.9 4.3 1.3]\n", " [5.7 2.8 4.1 1.3]\n", " [6.3 3.3 6. 2.5]\n", " [7.1 3. 5.9 2.1]\n", " [6.3 2.9 5.6 1.8]\n", " [6.5 3. 5.8 2.2]\n", " [4.9 2.5 4.5 1.7]\n", " [6.7 2.5 5.8 1.8]\n", " [7.2 3.6 6.1 2.5]\n", " [6.4 2.7 5.3 1.9]\n", " [6.8 3. 5.5 2.1]\n", " [5.7 2.5 5. 2. ]\n", " [5.8 2.8 5.1 2.4]\n", " [6.4 3.2 5.3 2.3]\n", " [6.5 3. 5.5 1.8]\n", " [7.7 3.8 6.7 2.2]\n", " [7.7 2.6 6.9 2.3]\n", " [6.9 3.2 5.7 2.3]\n", " [5.6 2.8 4.9 2. ]\n", " [7.7 2.8 6.7 2. ]\n", " [6.3 2.7 4.9 1.8]\n", " [6.7 3.3 5.7 2.1]\n", " [7.2 3.2 6. 1.8]\n", " [6.2 2.8 4.8 1.8]\n", " [6.1 3. 4.9 1.8]\n", " [6.4 2.8 5.6 2.1]\n", " [7.2 3. 5.8 1.6]\n", " [7.4 2.8 6.1 1.9]\n", " [6.4 2.8 5.6 2.2]\n", " [6.1 2.6 5.6 1.4]\n", " [7.7 3. 6.1 2.3]\n", " [6.4 3.1 5.5 1.8]\n", " [6. 3. 4.8 1.8]\n", " [5.8 2.7 5.1 1.9]\n", " [6.7 3. 5.2 2.3]\n", " [6.5 3. 5.2 2. ]\n", " [5.9 3. 5.1 1.8]]\n" ] } ], "source": [ "# create a selection variable which will have 75% True and 25% False values. The size of the selection variable is 150\n", "iris_selection = np.random.choice(\n", " [True, False], 150, replace=True, p=[0.75, 0.25])\n", "# create an iris dataset using the selection variable\n", "data = iris.data[iris_selection]\n", "print(data)" ] }, { "cell_type": "code", "execution_count": 21, "metadata": {}, "outputs": [], "source": [ "# create a cuml UMAP model \n", "fitter = UMAP(n_neighbors=10, min_dist=0.01, verbose=False)\n", "# fit the data created the selection variable to the cuml UMAP model created (fitter)\n", "fitter.fit(data)\n", "# create a new iris dataset by inverting the values of the selection variable (ie. 75% False and 25% True values) \n", "new_data = iris.data[~iris_selection]\n", "# transform the new data using the previously created embedded space\n", "embedding = fitter.transform(new_data)" ] }, { "cell_type": "code", "execution_count": 22, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "0.9513419913419914\n" ] } ], "source": [ "# calculate the trustworthiness score for the new data created (new_data)\n", "trust = trustworthiness(new_data, embedding, 10)\n", "print(trust)" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [] } ], "metadata": { "kernelspec": { "display_name": "Python 3", "language": "python", "name": "python3" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 3 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", "version": "3.7.3" } }, "nbformat": 4, "nbformat_minor": 2 }