//NonLeafElement.java // //This library is free software; you can redistribute it and/or //modify it under the terms of the GNU Lesser General Public //License as published by the Free Software Foundation; either //version 2.1 of the License, or (at your option) any later version. // //This library is distributed in the hope that it will be useful, //but WITHOUT ANY WARRANTY; without even the implied warranty of //MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU //Lesser General Public License for more details. package rtree; /** Anybody outside the package need not be concerned with this class. Element that will be in a non leaf node @author Prachuryya Barua */ public class NonLeafElement extends Element { /**will contain file pointer pointing to the child node*/ long nodePtr; public NonLeafElement( Rect nodeRect,long nodePtr) { super(nodeRect); this.nodePtr = nodePtr; } /**if possible make this function abstract and static in the parent class depends upon the size of the pointer */ public static int sizeInBytes() { return( Rect.sizeInBytes() + Node.LONG_SIZE); } /** This can be the chile node pointer. */ // public Object getPtr()//this is an integer object // { // return(new Integer(nodePtr)); // } public long getPtr()//this is an integer object { return nodePtr; } public int getElementType() { return Node.NONLEAF_NODE; } // void setPtr(Object ptr) // throws IllegalValueException // { // if(!(ptr instanceof Integer)) // throw new IllegalValueException("rtree.NonLeafElement.setPtr: pointer shoild be Integer"); // nodePtr = ((Integer)ptr).intValue(); // } public void setPtr(long ptr) { nodePtr = ptr; } public String toString() { return (super.toString()+"\n\tnodePointer: "+nodePtr); } /** A merge-sort routine for the Packing algo. @param rect the array to sort @param on if 0 then sort on X else on Y(i.e for 1) */ public static void sort( Element[] elmts,int on) { twoWayMerge(elmts,0,elmts.length-1,on); } static void twoWayMerge(Element[] elmts,int start,int finish,int on) { try{ int size = finish - start+1; if(size <= 2){//last two elements - simple swap if(size < 2) return; int midValI = getMid(elmts[start],on); int midValJ = getMid(elmts[finish],on); Element temp; if(midValI > midValJ){ temp = elmts[start]; elmts[start] = elmts[finish]; elmts[finish] = temp; } return; } Double middle = new Double(start+finish); middle = new Double(Math.ceil(middle.doubleValue()/2)); twoWayMerge(elmts,start,middle.intValue(),on); twoWayMerge(elmts,middle.intValue(),finish,on); simpleMerge(elmts,start,middle.intValue(),finish,on); } catch(Exception e){ System.out.println("rtree.Element.twoWayMerge: probably index out of bound"); //e.printStackTrace(); } } //simple merge private static void simpleMerge( Element[] elmts,int first,int second,int third,int on) throws Exception { int i = first; int j = second; int l = 0; int midValI; int midValJ; Element[] temp = new Element[third-first+1]; while((i < second) && (j <= third)){//loop till one lasts //get the mid values in the given dimension midValI = getMid(elmts[i],on); midValJ = getMid(elmts[j],on); if(midValI <= midValJ) temp[l++] = elmts[i++]; else temp[l++] = elmts[j++]; } //copy the rest if(i >= second)//give second section while(j <= third) temp[l++] = elmts[j++]; else while(i < second)//give first section temp[l++] = elmts[i++]; System.arraycopy(temp,0,elmts,first,temp.length); } /** A private class to calculate the mid value in given dimension */ private static int getMid( Element elmt,int on) { if(on == 0) return ((elmt.getRect().getMaxX() + elmt.getRect().getMinX())/2); else return ((elmt.getRect().getMaxY() + elmt.getRect().getMinY())/2); } public Object clone() { try{ return new NonLeafElement(new Rect(Rectangle.getMinX(), Rectangle.getMinY(), Rectangle.getMaxX(), Rectangle.getMaxY()), nodePtr); } catch(Exception e){ e.printStackTrace(); return null; } } }