Exemplo n.º 1
0
        /// <summary>
        /// Initialize a tree node.
        /// </summary>
        private static SHPTreeNode NodeCreate(double[] padfBoundsMin,
                                              double[] padfBoundsMax)

        {
            SHPTreeNode psTreeNode;

            psTreeNode = new SHPTreeNode();

            psTreeNode.nShapeCount  = 0;
            psTreeNode.panShapeIds  = null;
            psTreeNode.papsShapeObj = null;

            psTreeNode.nSubNodes = 0;

            if (padfBoundsMin != null)
            {
                c.memcpy(psTreeNode.adfBoundsMin, padfBoundsMin, sizeof(double) * 4);
            }

            if (padfBoundsMax != null)
            {
                c.memcpy(psTreeNode.adfBoundsMax, padfBoundsMax, sizeof(double) * 4);
            }

            return(psTreeNode);
        }
Exemplo n.º 2
0
        /************************************************************************/
        /*                          SHPTreeNodeTrim()                           */
        /*                                                                      */
        /*      This is the recurve version of SHPTreeTrimExtraNodes() that     */
        /*      walks the tree cleaning it up.                                  */
        /************************************************************************/

        private static bool NodeTrim(SHPTreeNode psTreeNode)

        {
            int i;

            /* -------------------------------------------------------------------- */
            /*      Trim subtrees, and free subnodes that come back empty.          */
            /* -------------------------------------------------------------------- */
            for (i = 0; i < psTreeNode.nSubNodes; i++)
            {
                if (NodeTrim(psTreeNode.apsSubNode[i]))
                {
                    DestroyNode(ref psTreeNode.apsSubNode[i]);

                    psTreeNode.apsSubNode[i] =
                        psTreeNode.apsSubNode[psTreeNode.nSubNodes - 1];

                    psTreeNode.nSubNodes--;

                    i--; /* process the new occupant of this subnode entry */
                }
            }

            /* -------------------------------------------------------------------- */
            /*      We should be trimmed if we have no subnodes, and no shapes.     */
            /* -------------------------------------------------------------------- */
            return(psTreeNode.nSubNodes == 0 && psTreeNode.nShapeCount == 0);
        }
Exemplo n.º 3
0
        /************************************************************************/
        /*                         SHPDestroyTreeNode()                         */
        /************************************************************************/
        private static void DestroyNode(ref SHPTreeNode psTreeNode)

        {
            int i;

            for (i = 0; i < psTreeNode.nSubNodes; i++)
            {
                if (psTreeNode.apsSubNode[i] != null)
                {
                    DestroyNode(ref psTreeNode.apsSubNode[i]);
                }
            }

            if (psTreeNode.panShapeIds != null)
            {
                c.free(ref psTreeNode.panShapeIds);
            }

            if (psTreeNode.papsShapeObj != null)
            {
                for (i = 0; i < psTreeNode.nShapeCount; i++)
                {
                    if (psTreeNode.papsShapeObj[i] != null)
                    {
                        psTreeNode.papsShapeObj[i] = null;
                    }
                }

                c.free(ref psTreeNode.papsShapeObj);
            }

            c.free(ref psTreeNode);
        }
Exemplo n.º 4
0
        /************************************************************************/
        /*                      SHPTreeCollectShapesIds()                       */
        /*                                                                      */
        /*      Work function implementing SHPTreeFindLikelyShapes() on a       */
        /*      tree node by tree node basis.                                   */
        /************************************************************************/
        public void CollectShapeIds(SHPTreeNode psTreeNode,
                                    double[] padfBoundsMin, double[] padfBoundsMax,
                                    ref int pnShapeCount, ref int pnMaxShapes,
                                    ref int[] ppanShapeList)

        {
            SHPTree hTree = this;   /* do not free! */

            int i;

            /* -------------------------------------------------------------------- */
            /*      Does this node overlap the area of interest at all?  If not,    */
            /*      return without adding to the list at all.                       */
            /* -------------------------------------------------------------------- */
            if (!CheckBoundsOverlap(psTreeNode.adfBoundsMin,
                                    psTreeNode.adfBoundsMax,
                                    padfBoundsMin,
                                    padfBoundsMax,
                                    hTree.nDimension))
            {
                return;
            }

            /* -------------------------------------------------------------------- */
            /*      Grow the list to hold the shapes on this node.                  */
            /* -------------------------------------------------------------------- */
            if (pnShapeCount + psTreeNode.nShapeCount > pnMaxShapes)
            {
                pnMaxShapes   = (pnShapeCount + psTreeNode.nShapeCount) * 2 + 20;
                ppanShapeList =
                    SfRealloc(ref ppanShapeList, pnMaxShapes);
            }

            /* -------------------------------------------------------------------- */
            /*      Add the local nodes shapeids to the list.                       */
            /* -------------------------------------------------------------------- */
            for (i = 0; i < psTreeNode.nShapeCount; i++)
            {
                ppanShapeList[pnShapeCount++] = psTreeNode.panShapeIds[i];
            }

            /* -------------------------------------------------------------------- */
            /*      Recurse to subnodes if they exist.                              */
            /* -------------------------------------------------------------------- */
            for (i = 0; i < psTreeNode.nSubNodes; i++)
            {
                if (psTreeNode.apsSubNode[i] != null)
                {
                    CollectShapeIds(psTreeNode.apsSubNode[i],
                                    padfBoundsMin, padfBoundsMax,
                                    ref pnShapeCount, ref pnMaxShapes,
                                    ref ppanShapeList);
                }
            }
        }
Exemplo n.º 5
0
        public static void free(ref SHPTreeNode memblock)

        {
            memblock = null;
        }
Exemplo n.º 6
0
        /************************************************************************/
        /*                       SHPTreeNodeAddShapeId()                        */
        /************************************************************************/
        private static bool NodeAddShapeId(
            SHPTreeNode psTreeNode, SHPObject psObject,
            int nMaxDepth, int nDimension)

        {
            int i;

            /* -------------------------------------------------------------------- */
            /*      If there are subnodes, then consider wiether this object        */
            /*      will fit in them.                                               */
            /* -------------------------------------------------------------------- */
            if (nMaxDepth > 1 && psTreeNode.nSubNodes > 0)
            {
                for (i = 0; i < psTreeNode.nSubNodes; i++)
                {
                    if (CheckObjectContained(psObject, nDimension,
                                             psTreeNode.apsSubNode[i].adfBoundsMin,
                                             psTreeNode.apsSubNode[i].adfBoundsMax))
                    {
                        return(NodeAddShapeId(psTreeNode.apsSubNode[i],
                                              psObject, nMaxDepth - 1,
                                              nDimension));
                    }
                }
            }

            /* -------------------------------------------------------------------- */
            /*      Otherwise, consider creating four subnodes if could fit into    */
            /*      them, and adding to the appropriate subnode.                    */
            /* -------------------------------------------------------------------- */
#if MAX_SUBNODE_QUAD
            else if (nMaxDepth > 1 && psTreeNode.nSubNodes == 0)
            {
                double[] adfBoundsMinH1 = new double[4], adfBoundsMaxH1 = new double[4];
                double[] adfBoundsMinH2 = new double[4], adfBoundsMaxH2 = new double[4];
                double[] adfBoundsMin1  = new double[4], adfBoundsMax1 = new double[4];
                double[] adfBoundsMin2  = new double[4], adfBoundsMax2 = new double[4];
                double[] adfBoundsMin3  = new double[4], adfBoundsMax3 = new double[4];
                double[] adfBoundsMin4  = new double[4], adfBoundsMax4 = new double[4];

                SplitBounds(psTreeNode.adfBoundsMin,
                            psTreeNode.adfBoundsMax,
                            adfBoundsMinH1, adfBoundsMaxH1,
                            adfBoundsMinH2, adfBoundsMaxH2);

                SplitBounds(adfBoundsMinH1, adfBoundsMaxH1,
                            adfBoundsMin1, adfBoundsMax1,
                            adfBoundsMin2, adfBoundsMax2);

                SplitBounds(adfBoundsMinH2, adfBoundsMaxH2,
                            adfBoundsMin3, adfBoundsMax3,
                            adfBoundsMin4, adfBoundsMax4);

                if (CheckObjectContained(psObject, nDimension,
                                         adfBoundsMin1, adfBoundsMax1) ||
                    CheckObjectContained(psObject, nDimension,
                                         adfBoundsMin2, adfBoundsMax2) ||
                    CheckObjectContained(psObject, nDimension,
                                         adfBoundsMin3, adfBoundsMax3) ||
                    CheckObjectContained(psObject, nDimension,
                                         adfBoundsMin4, adfBoundsMax4))
                {
                    psTreeNode.nSubNodes     = 4;
                    psTreeNode.apsSubNode[0] = NodeCreate(adfBoundsMin1,
                                                          adfBoundsMax1);
                    psTreeNode.apsSubNode[1] = NodeCreate(adfBoundsMin2,
                                                          adfBoundsMax2);
                    psTreeNode.apsSubNode[2] = NodeCreate(adfBoundsMin3,
                                                          adfBoundsMax3);
                    psTreeNode.apsSubNode[3] = NodeCreate(adfBoundsMin4,
                                                          adfBoundsMax4);

                    /* recurse back on this node now that it has subnodes */
                    return(NodeAddShapeId(psTreeNode, psObject,
                                          nMaxDepth, nDimension));
                }
            }
#else // MAX_SUBNODE_QUAD
            /* -------------------------------------------------------------------- */
            /*      Otherwise, consider creating two subnodes if could fit into     */
            /*      them, and adding to the appropriate subnode.                    */
            /* -------------------------------------------------------------------- */
            else if (nMaxDepth > 1 && psTreeNode.nSubNodes == 0)
            {
                double[] adfBoundsMin1 = new double[4], adfBoundsMax1 = new double[4];
                double[] adfBoundsMin2 = new double[4], adfBoundsMax2 = new double[4];

                SplitBounds(psTreeNode.adfBoundsMin, psTreeNode.adfBoundsMax,
                            adfBoundsMin1, adfBoundsMax1,
                            adfBoundsMin2, adfBoundsMax2);

                if (CheckObjectContained(psObject, nDimension,
                                         adfBoundsMin1, adfBoundsMax1))
                {
                    psTreeNode.nSubNodes     = 2;
                    psTreeNode.apsSubNode[0] = NodeCreate(adfBoundsMin1,
                                                          adfBoundsMax1);
                    psTreeNode.apsSubNode[1] = NodeCreate(adfBoundsMin2,
                                                          adfBoundsMax2);

                    return(NodeAddShapeId(psTreeNode.apsSubNode[0], psObject,
                                          nMaxDepth - 1, nDimension));
                }
                else if (CheckObjectContained(psObject, nDimension,
                                              adfBoundsMin2, adfBoundsMax2))
                {
                    psTreeNode.nSubNodes     = 2;
                    psTreeNode.apsSubNode[0] = NodeCreate(adfBoundsMin1,
                                                          adfBoundsMax1);
                    psTreeNode.apsSubNode[1] = NodeCreate(adfBoundsMin2,
                                                          adfBoundsMax2);

                    return(NodeAddShapeId(psTreeNode.apsSubNode[1], psObject,
                                          nMaxDepth - 1, nDimension));
                }
            }
#endif // MAX_SUBNODE_QUAD

            /* -------------------------------------------------------------------- */
            /*      If none of that worked, just add it to this nodes list.         */
            /* -------------------------------------------------------------------- */
            psTreeNode.nShapeCount++;

            psTreeNode.panShapeIds =
                SfRealloc(ref psTreeNode.panShapeIds,
                          psTreeNode.nShapeCount);
            psTreeNode.panShapeIds[psTreeNode.nShapeCount - 1] = psObject.nShapeId;

            if (psTreeNode.papsShapeObj != null)
            {
                psTreeNode.papsShapeObj =
                    SfRealloc(ref psTreeNode.papsShapeObj,
                              psTreeNode.nShapeCount);
                psTreeNode.papsShapeObj[psTreeNode.nShapeCount - 1] = null;
            }

            return(true);
        }