Example #1
0
        public static SolveResults ComputeSOM(KMap _som)
        {
            SolveResults result = new SolveResults();

            _som.trainNodes();
            _som.outputNodeWeights();
            _som.iter++;
            result.Value = _som;
            return(result);
        }
Example #2
0
        /// <summary>
        /// This is the method that actually does the work.
        /// </summary>
        /// <param name="DA">The DA object is used to retrieve from inputs and store in outputs.</param>
        protected override void SolveInstance(IGH_DataAccess DA)
        {
            colors = new List <System.Drawing.Color>();
            pNames = new List <string>();
            pAreas = new List <double>();
            List <Rectangle3d>       rects = new List <Rectangle3d>();
            GH_Structure <GH_Number> pData;
            GH_Structure <GH_Number> pWeights;
            List <Point3d>           points = new List <Point3d>();

            DataTree <double> mod_pData;
            DataTree <double> mod_pWeights;
            string            message = "nothing";
            bool optimized            = false;
            int  numMetrics           = -1;


            DA.GetData(IN_numMetrics, ref numMetrics);
            DA.GetData(IN_reset, ref reset);
            DA.GetData(IN_run, ref run);
            DA.GetData(IN_mode, ref optimized);
            DA.GetDataList(IN_programNames, pNames);
            DA.GetDataList(IN_programAreas, pAreas);
            DA.GetDataTree(IN_programData, out pData);
            DA.GetDataList(IN_programColors, colors);
            DA.GetDataList(IN_pRects, rects);
            DA.GetDataTree(IN_pWeights, out pWeights);
            DA.GetData(IN_resolution, ref _resolution);
            DA.GetData(IN_radMultiplier, ref radiusMultiplier);
            DA.GetData(IN_showSOM, ref showSOM);
            DA.GetData(IN_SOMDisplay, ref display);
            DA.GetData(IN_DisplayLabels, ref displayText);

            if (run)
            {
                isRunning = true;
            }
            else
            {
                isRunning = false;
            }

            if (isRunning)
            {
                ExpireSolution(true);
            }

            var simpleNameTree = new DataTree <string>();

            try
            {
                if (reset || SOM == null)
                {
                    circles = new List <Polyline>();
                    points  = new List <Point3d>();

                    radii        = new List <double>();
                    gradientList = new List <System.Drawing.Color>();

                    for (int i = 0; i < rects.Count; i++)
                    {
                        points.Add(rects[i].Center);
                    }

                    for (int i = 0; i < pAreas.Count; i++)
                    {
                        var rad = Math.Sqrt(pAreas[i] / Math.PI);
                        radii.Add(rad * radiusMultiplier);
                    }

                    mod_pData    = new DataTree <double>();
                    mod_pWeights = new DataTree <double>();


                    for (int i = 0; i < pData.Paths.Count; i++)
                    {
                        var path = pData.get_Branch(i);
                        for (int j = 0; j < path.Count; j++)
                        {
                            var p    = new GH_Path(i);
                            var prog = pData.get_DataItem(p, j).Value;
                            mod_pData.Add(prog, new GH_Path(i));
                        }
                    }
                    for (int i = 0; i < pWeights.Paths.Count; i++)
                    {
                        var path = pWeights.get_Branch(i);
                        for (int j = 0; j < path.Count; j++)
                        {
                            var p      = new GH_Path(i);
                            var weight = pWeights.get_DataItem(p, j).Value;
                            mod_pWeights.Add(weight, new GH_Path(i));
                        }
                    }

                    //DA.SetDataTree(OUT_nodeWeights,mod_pWeights);
                    SOM = new KMap(mod_pData, points, _resolution, mod_pWeights, numMetrics, 0.12, radii, 1.0, maximumIterations);

                    SOM.applyProgramInputs(pNames.Count);
                    SOM.outputNodesXY();
                    reset = false;
                }


                if (SOM.iter < maximumIterations)
                {
                    if (InPreSolve)
                    {
                        Task <SolveResults> task = Task.Run(() => ComputeSOM(SOM), CancelToken);
                        TaskList.Add(task);
                        return;
                    }

                    if (!GetSolveResults(DA, out SolveResults result))
                    {
                        result = ComputeSOM(SOM);
                        SOM    = result.Value;
                    }

                    message = string.Format("Runnning...{0}/{1} iterations", SOM.iter, maximumIterations);
                }
                else
                {
                    message   = "Done.";
                    isRunning = false;
                    run       = false;
                    ClearData();
                }

                if (showSOM)
                {
                    var nL = new List <double>();
                    SOM.nodeWeights.Clear();
                    for (int i = 0; i < SOM.nodeW.BranchCount; i++)
                    {
                        GH_Path path         = SOM.nodeW.Path(i);
                        int     elementCount = SOM.nodeW.Branch(i).Count;
                        double  average      = 0;

                        for (int j = 0; j < elementCount; j++)
                        {
                            average += SOM.nodeW[path, j];
                        }

                        average /= elementCount;

                        nL.Add(average); //average value of all dims of a node
                    }

                    SOM.nodeWeights = nL;

                    Remapper re = new Remapper(SOM.nodeWeights, SOM.nodePoints, pNames, pAreas, _resolution, optimized);


                    var n     = re.nodes;
                    var _tree = re.programTree;


                    ///silly name tree output as requested..
                    for (int i = 0; i < _tree.BranchCount; i++)
                    {
                        simpleNameTree.Add(_tree.Branch(i)[0].name.Split('_')[0], new GH_Path(i));
                    }


                    //'tree' below is the sorted nodes corresponding to each program based on their BMU
                    var tempTree = new DataTree <sNode>();

                    for (int i = 0; i < _tree.BranchCount; i++)
                    {
                        int localBCount = _tree.Branch(i).Count;

                        var orderedBranch = _tree.Branch(i).OrderBy(c => c.multiplierStrength).ToList();
                        tempTree.AddRange(orderedBranch, new GH_Path(i));
                    }

                    SOM.tree.Clear();
                    for (int i = 0; i < tempTree.BranchCount; i++)
                    {
                        var fPath       = tempTree.Path(i);
                        int localBCount = tempTree.Branch(i).Count;

                        for (int j = 0; j < localBCount; j++)
                        {
                            Plane    plane = new Plane(tempTree.Branch(i)[j].pos, Vector3d.ZAxis);
                            Interval inter = new Interval(-_resolution * 0.5, _resolution * 0.5);
                            var      rect  = new Rectangle3d(plane, inter, inter);
                            var      poly  = rect.ToPolyline();
                            //circles.Add(poly);

                            SOM.tree.Add(poly, new GH_Path(fPath));
                        }
                    }

                    //data for visualization

                    var _points = new List <Point3d>();
                    SOM.m_pNames = new List <string>();
                    for (int i = 0; i < n.Count; i++)
                    {
                        var p          = n[i].pos;
                        var name       = n[i].name;
                        var multiplier = n[i].multiplierStrength;
                        _points.Add(p);
                        SOM.m_pNames.Add(name);
                    }


                    //color by gradient colors
                    // for (int i = 0; i < nodeWeights.Count; i++)

                    if (display == 1)
                    {
                        gradientList = new List <System.Drawing.Color>();
                        for (int i = 0; i < n.Count; i++)
                        {
                            var multiplier = n[i].multiplierStrength;
                            var gColor     = new ColorHSL(multiplier, 0, multiplier);

                            var rgb = gColor.ToArgbColor();
                            gradientList.Add(rgb);
                        }
                    }

                    else if (display == 2)
                    {
                        gradientList = new List <System.Drawing.Color>();
                        for (int i = 0; i < n.Count; i++)
                        {
                            var gColor = new ColorHSL(SOM.nodeWeights[i], SOM.nodeWeights[i], SOM.nodeWeights[i], SOM.nodeWeights[i]);

                            var rgb = gColor.ToArgbColor();
                            gradientList.Add(rgb);
                        }
                    }


                    for (int i = 0; i < SOM.m_pNames.Count; i++)
                    {
                        for (int j = 0; j < pNames.Count; j++)
                        {
                            var strippedName = SOM.RemoveNumbersSymbols(SOM.m_pNames[i]);
                            if (strippedName == pNames[j])
                            {
                                SOM.discreteCol.Add(colors[j]);
                            }
                        }
                    }
                    SOM.drawingPolys.Clear();
                    SOM.drawCircles();

                    circles = SOM.drawingPolys;
                }
            }
            catch (Exception e)
            {
                AddRuntimeMessage(GH_RuntimeMessageLevel.Error, e.ToString());
            }

            DA.SetData(OUT_RunFeedback, message);
            DA.SetDataList(OUT_nodeWeights, SOM.nodeWeights);
            DA.SetDataTree(OUT_programTree, SOM.tree);
            DA.SetDataTree(OUT_programNames, simpleNameTree);
        }