コード例 #1
0
        }//dfs

        public static void Clustring(int K)// make clustring
        {
            /*
             * Total complexty  is O(MST count) = distincit + O(d log K)
             */
            adj_lst      = new Dictionary <int, List <int> >(); // initialize adjacency list
            Node_Cluster = new int[16777216];                   // which node assigned to which cluster
            vis          = new bool[16777216];                  // visited array described before
            RGBPixel Val;


            int sz1 = MST.Count;

            for (int i = 1; i < sz1; i++)   // mov in size of mst = d
            {
                if (VX.ContainsKey(MST[i])) // if this edge will be cutt
                {
                    /*add it to adjecency list*/
                    if (!adj_lst.ContainsKey(MST[i].from))
                    {
                        adj_lst.Add(MST[i].from, new List <int>());
                    }
                    if (!adj_lst.ContainsKey(MST[i].to))
                    {
                        adj_lst.Add(MST[i].to, new List <int>());
                    }
                }
                else // if this edge will not be cutt
                {
                    /*add it to adjecency list*/
                    if (!adj_lst.ContainsKey(MST[i].from))
                    {
                        adj_lst.Add(MST[i].from, new List <int> {
                            MST[i].to
                        });
                    }
                    else
                    {
                        adj_lst[MST[i].from].Add(MST[i].to);
                    }
                    if (!adj_lst.ContainsKey(MST[i].to))
                    {
                        adj_lst.Add(MST[i].to, new List <int> {
                            MST[i].from
                        });
                    }
                    else
                    {
                        adj_lst[MST[i].to].Add(MST[i].from);
                    }
                }
            }

            int sz = H.Count;

            while (sz > 0)             // move in the number of cutted edges
            {
                GRAPH R = H.Dequeue(); // dequeue the first edge with complexty O(log K)
                sz--;
                Number_Nodes = 0;

                if (!vis[R.from]) // if the from is not visited
                {
                    Number_Nodes = 0; Rd = G = B = 0; dfs(R.from); Rd /= Number_Nodes; G /= Number_Nodes; B /= Number_Nodes;
                    Val.red      = (byte)Rd; Val.green = (byte)G; Val.blue = (byte)B;
                    /*shift the accumilated red green blue from this cluster*/
                    int ind1 = Val.red << 8 | Val.green;
                    int ind  = ind1 << 8 | Val.blue;
                    nodes[Cluster_Number] = ind;// reuse the nodes to add the average of this cluster
                    Cluster_Number++;
                }
                if (!vis[R.to])// if the from is not visited
                {
                    Number_Nodes = 0; Rd = G = B = 0; dfs(R.to); Rd /= Number_Nodes; G /= Number_Nodes; B /= Number_Nodes;
                    Val.red      = (byte)Rd; Val.green = (byte)G; Val.blue = (byte)B;
                    /*shift the accumilated red green blue from this cluster*/
                    int ind1 = Val.red << 8 | Val.green;
                    int ind  = ind1 << 8 | Val.blue;
                    nodes[Cluster_Number] = ind;// reuse the nodes to add the average of this cluster
                    Cluster_Number++;
                }
            }
        }//Clustring
コード例 #2
0
        }             //get_distincit

        public static void grph(int CLUS)// graph construction and getting edges that will be cut that take number of clusters
        {
            /*
             * Total complexty = O (E log (k))
             *           --where E is the number of edges and K is the number of clusters wanted to cut
             */
            float min = 10000000, newedge;
            //min is minimum value that take from moving from exesting node to another node, newedge is edge between exesting node to another node
            int k = 0, count = nodes.Count;               //k is the index of minimum node that i would start in next time

            bool[] vstd = new bool[16777216];             //to check if node has been visited before (get values between it and all another none visited nodes)
            VX = new Dictionary <GRAPH, float>();         // initialize th helper of periority_queue
            H  = new FastPriorityQueue <GRAPH>(CLUS - 1); //initialize periority_queue

            for (int i = k; ;)                            //first loop to move in distincit node
            {
                bool ch = false;                          // if it still false then i can't go anywhere because all nodes have been visited
                if (vstd[nodes[i]])
                {
                    continue;                   // if the node that i stand in is visited then continue
                }
                vstd[nodes[i]] = true;          //this not is not visited before then make it as visited
                min            = 10000000;      // give minimum every time very large value
                for (int j = 0; j < count; j++) //second loop to move in distincit node
                {
                    if (vstd[nodes[j]])
                    {
                        continue; //if the node that i stand in is visited then continue
                    }
                    ch = true;    //then it i found another node to move in
                    byte[] b = BitConverter.GetBytes(nodes[i]), bb = BitConverter.GetBytes(nodes[j]);
                    // convert the shifted integer to red and green and blue
                    newedge = (((b[0] - bb[0]) * (b[0] - bb[0])) + ((b[1] - bb[1]) * (b[1] - bb[1])) + ((b[2] - bb[2]) * (b[2] - bb[2])));
                    //calculate the edge between to nodes
                    if (newedge < min)                //if the edge i have less than minimum then
                    {
                        min = newedge;                //make the minimum is newedge
                        k   = j;                      //and save its index to start from it the next time
                    }
                    if (MST[j].edge < min)            // if the edge that is already saved is less than minimum then
                    {
                        min = MST[j].edge;            //make the minimum is saved edge
                        k   = j;                      //and save its index to start from it the next time
                    }
                    if (newedge < (float)MST[j].edge) // if the calculated edge before is larger than the newly calculated edge then
                    {
                        MST[j].edge = newedge;        //then replace the calculaed edge with the new minimum edge
                        MST[j].from = nodes[i];       //and change from where it comes
                    }
                }
                i = k;                                      //K is the minimum index that i will start the loop with
                if (ch == false)                            // then i cant go to any node again because all nodes have been visited then choose the cutted edges
                {
                    GRAPH T = new GRAPH();                  //temp to delete the deleted edge from dictionary as it is deleted from periority_queue
                    for (int y = 1; y < MST.Count; y++)     //move in all Minimum spanning tree
                    {
                        if (H.Count < CLUS - 1)             // if the periority_queue is not filled with required number of clusters then
                        {
                            H.Enqueue(MST[y], MST[y].edge); // add in periority_queue with complexty O(log K) k is the wanted number of clusters
                            VX.Add(MST[y], MST[y].edge);    // add in the dictionary this edge
                        }
                        else//if the periority_queue is  filled with required number of clusters then
                        {
                            if (H.First.edge < MST[y].edge)     //check if the edge that i stand is larger than the top of queue that contain the smallest edge
                            {
                                T = H.Dequeue();                //pop the smallest from the queue
                                VX.Remove(T);                   //remove also this node from dictionary
                                H.Enqueue(MST[y], MST[y].edge); //enqueue the new large node with the new large edge with complexty O(log K)
                                VX.Add(MST[y], MST[y].edge);    //add the new large node with the new large edge
                            }
                        }
                    }
                }
                if (!ch)
                {
                    break;      //if i can't go anywhere then break
                }
            }//main loop
             /* this to get cost of minimum spanning tree*/

            /*   double sum = 0;
             * for (int i = 1; i < MST.Count; i++)
             * {
             *     sum += Math.Sqrt(MST[i].edge);
             * }
             * MessageBox.Show(sum.ToString());*/
        }