Exemplo n.º 1
0
        public static void FindsABParamsUsingLevenbergMarquardtForDefaultSettings()
        {
            const float expectedA = 1.5769434603113077f;
            const float expectedB = 0.8950608779109733f;

            var(a, b) = Umap.FindABParams(1, 0.1f);
            Assert.True(AreCloseEnough(a, expectedA));
            Assert.True(AreCloseEnough(b, expectedB));

            bool AreCloseEnough(float x, float y) => Math.Abs(x - y) < 0.01;
        }
Exemplo n.º 2
0
        public static void FindsNearestNeighbors()
        {
            var nNeighbors = 10;
            var umap       = new Umap(random: new DeterministicRandomGenerator(42), numberOfNeighbors: nNeighbors);

            var(knnIndices, knnDistances) = umap.NearestNeighbors(TestData, progress => { });

            Assert.Equal(knnDistances.Length, TestData.Length);
            Assert.Equal(knnIndices.Length, TestData.Length);

            Assert.Equal(knnDistances[0].Length, nNeighbors);
            Assert.Equal(knnIndices[0].Length, nNeighbors);
        }
Exemplo n.º 3
0
        // Main
        static void Main(string[] args)
        {
            // Download the MNIST data from Mr. YannAndréLeCun's web site
            using (var wc = new WebClient())
            {
                if (!File.Exists(LABEL_FILE_NAME))
                {
                    wc.DownloadFile(LABEL_FILE_URL, LABEL_FILE_NAME);
                }
                if (!File.Exists(IMAGE_FILE_NAME))
                {
                    wc.DownloadFile(IMAGE_FILE_URL, IMAGE_FILE_NAME);
                }
            }

            // Load the MNIST labels
            var labels = GetLabels().ToArray();

            // Load the MNIST image data
            var pixels = GetImages().ToArray();

            // Dimension reduction with UMAP
            var umap   = new Umap();
            var epochs = umap.InitializeFit(pixels);

            for (var i = 0; i < epochs; ++i)
            {
                umap.Step();
            }
            var embedding = umap.GetEmbedding().AsEnumerable();

            // Convert the embedding into chart data
            var graph = new Graph.Scatter()
            {
                x      = embedding.Select((o) => o[0]),
                y      = embedding.Select((o) => o[1]),
                text   = labels.Select((o) => o.ToString()),
                mode   = "markers",
                marker = new Graph.Marker {
                    color = labels, colorscale = "Rainbow", showscale = true
                },
            };

            var chart = Chart.Plot(graph);

            chart.WithTitle("MNIST Embedded via UMAP");
            chart.WithXTitle("X");
            chart.WithYTitle("Y");
            chart.WithSize(800, 800);
            chart.Show();
        }
Exemplo n.º 4
0
        public static void StepMethod3D()
        {
            var umap    = new Umap(random: new DeterministicRandomGenerator(42), dimensions: 3);
            var nEpochs = umap.InitializeFit(TestData);

            for (var i = 0; i < nEpochs; i++)
            {
                umap.Step();
            }

            var embedding = umap.GetEmbedding();

            Assert.Equal(500, nEpochs);
            AssertNestedFloatArraysEquivalent(TestResults3D, embedding);
        }
Exemplo n.º 5
0
        static void Main()
        {
            // Note: The MNIST data here consist of normalized vectors (so the CosineForNormalizedVectors distance function can be safely used)
            var data = MessagePackSerializer.Deserialize <LabelledVector[]>(File.ReadAllBytes("MNIST-LabelledVectorArray-60000x100.msgpack"));

            data = data.Take(10_000).ToArray();

            var timer = Stopwatch.StartNew();
            var umap  = new Umap(distance: Umap.DistanceFunctions.CosineForNormalizedVectors);

            Console.WriteLine("Initialize fit..");
            var nEpochs = umap.InitializeFit(data.Select(entry => entry.Vector).ToArray());

            Console.WriteLine("- Done");
            Console.WriteLine();
            Console.WriteLine("Calculating..");
            for (var i = 0; i < nEpochs; i++)
            {
                umap.Step();
                if ((i % 10) == 0)
                {
                    Console.WriteLine($"- Completed {i + 1} of {nEpochs}");
                }
            }
            Console.WriteLine("- Done");
            var embeddings = umap.GetEmbedding()
                             .Select(vector => new { X = vector[0], Y = vector[1] })
                             .ToArray();

            timer.Stop();
            Console.WriteLine("Time taken: " + timer.Elapsed);

            // Fit the vectors to a 0-1 range (this isn't necessary if feeding these values down from a server to a browser to draw with Plotly because ronend because Plotly scales the axes to the data)
            var minX             = embeddings.Min(vector => vector.X);
            var rangeX           = embeddings.Max(vector => vector.X) - minX;
            var minY             = embeddings.Min(vector => vector.Y);
            var rangeY           = embeddings.Max(vector => vector.Y) - minY;
            var scaledEmbeddings = embeddings
                                   .Select(vector => new { X = (vector.X - minX) / rangeX, Y = (vector.Y - minY) / rangeY })
                                   .ToArray();

            const int width  = 1600;
            const int height = 1200;

            using (var bitmap = new Bitmap(width, height))
            {
                using (var g = Graphics.FromImage(bitmap))
                {
                    g.FillRectangle(Brushes.DarkBlue, 0, 0, width, height);
                    g.SmoothingMode     = SmoothingMode.HighQuality;
                    g.TextRenderingHint = TextRenderingHint.ClearTypeGridFit;
                    g.InterpolationMode = InterpolationMode.HighQualityBicubic;
                    g.PixelOffsetMode   = PixelOffsetMode.HighQuality;
                    using (var font = new Font("Tahoma", 6))
                    {
                        foreach (var(vector, uid) in scaledEmbeddings.Zip(data, (vector, entry) => (vector, entry.UID)))
                        {
                            g.DrawString(uid, font, Brushes.White, vector.X * width, vector.Y * height);
                        }
                    }
                }
                bitmap.Save("Output-Label.png");
            }

            var colors = "#006400,#00008b,#b03060,#ff4500,#ffd700,#7fff00,#00ffff,#ff00ff,#6495ed,#ffdab9"
                         .Split(',')
                         .Select(c => ColorTranslator.FromHtml(c))
                         .Select(c => new SolidBrush(c))
                         .ToArray();

            using (var bitmap = new Bitmap(width, height))
            {
                using (var g = Graphics.FromImage(bitmap))
                {
                    g.FillRectangle(Brushes.White, 0, 0, width, height);
                    g.SmoothingMode     = SmoothingMode.HighQuality;
                    g.InterpolationMode = InterpolationMode.HighQualityBicubic;
                    g.PixelOffsetMode   = PixelOffsetMode.HighQuality;
                    foreach (var(vector, uid) in scaledEmbeddings.Zip(data, (vector, entry) => (vector, entry.UID)))
                    {
                        g.FillEllipse(colors[int.Parse(uid)], vector.X * width, vector.Y * height, 5, 5);
                    }
                }
                bitmap.Save("Output-Color.png");
            }

            Console.WriteLine("Generated visualisation images");
            Console.WriteLine("Press [Enter] to terminate..");
            Console.ReadLine();
        }