From 8f27e65bddd7d4b8515ce620fb485fdd78fcdf89 Mon Sep 17 00:00:00 2001 From: Constantin Jucovschi Date: Fri, 24 Apr 2009 07:20:22 -0400 Subject: Initial commit --- java/rasj/RasMInterval.java | 1332 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 1332 insertions(+) create mode 100644 java/rasj/RasMInterval.java (limited to 'java/rasj/RasMInterval.java') diff --git a/java/rasj/RasMInterval.java b/java/rasj/RasMInterval.java new file mode 100644 index 0000000..dec1e3c --- /dev/null +++ b/java/rasj/RasMInterval.java @@ -0,0 +1,1332 @@ +package rasj; + +import java.lang.*; +import java.util.*; + +/* +* This file is part of rasdaman community. +* +* Rasdaman community is free software: you can redistribute it and/or modify +* it under the terms of the GNU General Public License as published by +* the Free Software Foundation, either version 3 of the License, or +* (at your option) any later version. +* +* Rasdaman community 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 General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with rasdaman community. If not, see . +* +* Copyright 2003, 2004, 2005, 2006, 2007, 2008, 2009 Peter Baumann / +rasdaman GmbH. +* +* For more information please see +* or contact Peter Baumann via . +*/ +/** *********************************************************** + *
+ *
+ * PURPOSE:
+ * The spatial domain of an MDD is represented by an object
+ * of class RasMInterval. It specifies lower and upper bound
+ * of the point set for each dimension of an MDD. Internally,
+ * the class is realized through an array of intervals of type
+ * RasSInterval.
+ *
+ * For the operations union, difference, and intersection the
+ * dimensionalties of the operands must be equal, otherwise an
+ * exception is raised. The semantics of the operations are
+ * defined as follows for each dimension:
+ *
+ *    | ...  fixed bound
+ *    -* ...  open bound
+ *
+ *
+ * class   orientation       union    difference  intersection
+ * -----------------------------------------------------------
+ *   1     |-a-| |-b-|       error    a           error
+ *
+ *   2     |-a-|             [a1,b2]  [a1,b1]     [b1,a2]
+ *   2        |-b-|
+ *
+ *   3     |--a--|           a        error       b
+ *   3      |-b-|
+ *
+ *   4     |-b-|             [b1,a2]  [b2,a2]     [a1,b2]
+ *   4        |-a-|
+ *
+ *   5     |--b--|           b        error       a
+ *   5      |-a-|
+ *
+ *   6     |-b-| |-a-|       error    a           error
+ *
+ *   7     |-a-|-b-|         [a1,b2]  a           [a2,a2]
+ *
+ *   8     |-b-|-a-|         [b1,a2]  a           [b2,b2]
+ *
+ *   9     |--a--|           a        [a1,b1]     b
+ *   9       |-b-|
+ *
+ *  10     |--a--|           a        [b2,a2]     b
+ *  10     |-b-|
+ *
+ *  11     |-a-|             a        error       a
+ *  11     |-b-|
+ *
+ *  12     |--b--|           b        error       a
+ *  12     |-a-|
+ *
+ *  13     |--b--|           b        error       a
+ *  13       |-a-|
+ *
+ *  -----------------------------------------------------
+ *
+ *  14     |--a--*           a        error       b
+ *  14      |-b-|
+ *
+ *  15     |--a--*           a        [b2,a2]     b
+ *  15     |-b-|
+ *
+ *  16     |-b-| |-a-*       error    a           error
+ *
+ *  17     |-b-|-a-*         [b1,a2]  a           [b2,b2]
+ *
+ *  18      |--a--*          [b1,a2]  [b2,a2]     [a1,b2]
+ *  18     |-b-|
+ *
+ *  -----------------------------------------------------
+ *
+ *  19     *--a--|          a        error       b
+ *  19      |-b-|
+ *
+ *  20     *--a--|          a        [a1,b1]     b
+ *  20       |-b-|
+ *
+ *  21     *-a-| |-b-|       error    a           error
+ *
+ *  22     *-a-|-b-|         [a1,b2]  a           [a2,a2]
+ *
+ *  23     *--a--|           [a1,b2]  [a1,b1]     [b1,a2]
+ *  23        |-b-|
+ *
+ *  -----------------------------------------------------
+ *
+ *  24     |--b--*           b        error       a
+ *  24      |-a-|
+ *
+ *  25     |--b--*           b        error       a
+ *  25     |-a-|
+ *
+ *  26     |-a-| |-b-*       error    a           error
+ *
+ *  27     |-a-|-b-*         [a1,b2]  a           [a2,a2]
+ *
+ *  28      |--b--*          [a1,b2]  [a1,b1]     [b1,a2]
+ *  28     |-a-|
+ *
+ *  -----------------------------------------------------
+ *
+ *  29     *--b--|           b        error       a
+ *  29      |-a-|
+ *
+ *  30     *--b--|           b        error       a
+ *  30       |-a-|
+ *
+ *  31     *-b-| |-a-|       error    a           error
+ *
+ *  32     *-b-|-a-|         [b1,a2]  a           [b2,b2]
+ *
+ *  33     *--b--|           [b1,a2]  [b2,a2]     [a1,b2]
+ *  33        |-a-|
+ *
+ *  -----------------------------------------------------
+ *
+ *  34     *-a-| |-b-*       error    a           error
+ *
+ *  35     *-a-|-b-*         [a1,b2]  a           [a2,a2]
+ *
+ *  36     *-a-|             [a1,b2]  [a1,b1]     [b1,a2]
+ *  36        |-b-*
+ *
+ *  -----------------------------------------------------
+ *
+ *  37     *-b-| |-a-*       error    a           error
+ *
+ *  38     *-b-|-a-*         [b1,a2]  a           [b2,b2]
+ *
+ *  39     *-b-|             [b1,a2]  [a1,b1]     [a1,b2]
+ *  39        |-a-*
+ *
+ *  -----------------------------------------------------
+ *
+ *  40     *-a-|             b        error       a
+ *  40      *-b-|
+ *
+ *  41     *-a-|             a        error       a
+ *  41     *-b-|
+ *
+ *  42     *-b-|             a        [b2,a2]     b
+ *  42      *-a-|
+ *
+ *  -----------------------------------------------------
+ *
+ *  43     |-a-*             a        [a1,b1]     b
+ *  43      |-b-*
+ *
+ *  44     |-a-*             a        error       a
+ *  44     |-b-*
+ *
+ *  45     |-b-*             b        error       a
+ *  45      |-a-*
+ *
+ *  -----------------------------------------------------
+ *  46     *-a-* |-b-|       a        error       b
+ *
+ *  47     *-b-* |-a-|       b        error       b
+ *
+ *  48     *-a-*             a        [b2,a2]     b
+ *  48      *-b-|
+ *
+ *  49     *-a-*             a        [a1,b1]     b
+ *  49      |-b-*
+ *
+ *  50     *-b-*             b        error       a
+ *  50      *-a-|
+ *
+ *  51     *-b-*             b        error       a
+ *  51      |-a-*
+ *
+ *  52     *-a-*             a        error       a
+ *  52     *-b-*
+ *
+ * Attention: The difference operation has to be reconsidered in future
+ * concerning a discrete interpretation of the intervals.
+ *
+ * The closure operation defines an interval which is the smallest
+ * interval containing the two operands.
+ * The method intersectsWith() returns false in the error cases of the
+ * intersection operation and true otherwise.
+ *
+ * * @version $Revision: 1.15 $
+ *
+ *
+ *
+ *
+ * COMMENTS:
+ *
+ * 
+ *********************************************************** */ + + +public class RasMInterval +{ + static final String rcsid = "@(#)Package rasj, class RasMInterval: $Header: /home/rasdev/CVS-repository/rasdaman/java/rasj/RasMInterval.java,v 1.15 2003/12/10 21:04:23 rasdev Exp $"; + + /** array for storing the intervals */ + protected RasSInterval[] intervals; + + /** dimensionality of the domain */ + protected int dimensionality; + + /** number of components initialized already */ + protected int streamInitCnt; + + /** + * Constructor getting dimensionality for stream initializing. + * @param dim the dimensionality of this MInterval + **/ + public RasMInterval(int dim) + { + dimensionality = dim; + streamInitCnt = 0; + intervals = new RasSInterval[dimensionality]; + + for(int i=0; i= dimensionality) + throw new RasStreamInputOverflowException(); + + intervals[streamInitCnt++] = newInterval; + + } + + /** + * Method for stream initialization with point intervals. + * @param p the point interval that has to be streamed + **/ + public void stream(long p) throws RasStreamInputOverflowException, RasResultIsNoIntervalException + { + if(streamInitCnt >= dimensionality) + throw new RasStreamInputOverflowException(); + + intervals[streamInitCnt++] = new RasSInterval(p, p); + + } + + /** + * Default constructor. + **/ + public RasMInterval() + { + dimensionality = 0; + streamInitCnt = 0; + + intervals = null; + } + + /** + * Copy constructor. + * @param mInterval the MInterval that is to be copied + **/ + public RasMInterval(final RasMInterval mInterval) + throws RasStreamInputOverflowException, RasIndexOutOfBoundsException + { + dimensionality = mInterval.dimension(); + streamInitCnt = mInterval.streamInitCnt; + intervals = new RasSInterval[ dimensionality ]; + + for(int i=0; i= dimensionality) + throw new RasIndexOutOfBoundsException(0, dimensionality-1, i); + + return intervals[i]; + } + + /** + * Write access to the i-th interval. + * @param i the dimension that is to be accessed + * @param value the interval that is to be assigned to the specified dimension + **/ + public void setItem(int i, RasSInterval value) throws RasIndexOutOfBoundsException + { + if(i < 0 || i >= dimensionality) + throw new RasIndexOutOfBoundsException(0, dimensionality-1, i); + intervals[i] = value; + } + + /* + * set MInterval + public final RasMInterval setTo(final RasMInterval mInterval) + throws RasStreamInputOverflowException, RasIndexOutOfBoundsException + { + if(this != mInterval) + { + if((intervals != null) && dimensionality != mInterval.dimension()) + { + intervals = null; + } + + dimensionality = mInterval.dimension(); + streamInitCnt = mInterval.streamInitCnt; + + if(intervals == null) + intervals = new RasSInterval[ dimensionality ]; + + for(int i=0; i + * -1 if the point has not the same dimensionality + * 1 if the point is covered by this MInterval + * 0 if the point is not covered + * + **/ + public final int covers(RasPoint pnt) + { + if (dimensionality != pnt.dimension()) + return -1; + try { + for (int i = 0; i < pnt.dimension(); i++) + { + if ((intervals[i].isLowFixed() && pnt.item(i) < intervals[i].low()) || + (intervals[i].isHighFixed() && pnt.item(i) > intervals[i].high())) + return 0; + } + return 1; + } + catch(RasIndexOutOfBoundsException e) { + // This cannot occur (theoretically) + throw new RasClientInternalException("RasMInterval","covers(RasPoint pnt)",e.getMessage()); + } + } + + /** + * Method for testing if this interval covers the given interval. + * @param inter2 the MInterval to be tested + * @return + * + * + * + * + **/ + public int covers(RasMInterval inter2) + { + if(dimensionality != inter2.dimension()) + return -1; + + try { + for (int i = 0; i < dimensionality ; i++) + { + if ( + ( intervals[i].isLowFixed() && + (!(inter2.item(i).isLowFixed()) || + intervals[i].low() > inter2.item(i).low() // both lows fixed here + ) + ) || // end of lows check + ( intervals[i].isHighFixed() && + (!(inter2.item(i).isHighFixed()) || + intervals[i].high() < inter2.item(i).high() // both highs fixed here + ) + ) + ) + return 0; + } + return 1; + } + catch( RasIndexOutOfBoundsException e) { + // this can not occur (theoretically) + throw new RasClientInternalException("RasMInterval","covers(RasMInterval inter2)",e.getMessage()); + } + } + + /** + * Gets the dimensionality of this MInterval. + * @return the dimensionality of this MInterval + **/ + public int dimension() + { + return dimensionality; + } + + /** + * Gets the point with the lowest coordinates in every dimension. + * @return the origin of this MInterval (the point with the lowest coordinates) + **/ + public RasPoint getOrigin() + { + try { + int i; + RasPoint pt = new RasPoint(dimensionality); + + for(i=0; i + * +-------------+---------------------------------------+ + * | A | B | + * +-------------|---------------------------------------| + * + * and the following two are not: + * + * +-------------+-------------------------+ + * | | B | + * | A +-------------------------+ + * +-------------+ + * + * + * @param b the MInterval to be checked + * @return true if the two intervalls are mergeable + **/ + public boolean isMergeable(final RasMInterval b) + { + final RasMInterval a = this; // An alias to this object + + // The blocks must have the same dimensionality to be mergeable + if (a.dimensionality != b.dimensionality) + return false; + + // Count the number of adjacent frontiers + int onesDifferences = 0; + + // Is Mergeable variable + boolean isMerg = true; + + // For all dimensions + try { + for (int i=0; i + * Note that this method modifies the current MInterval. If you want to + * get a new MInterval, use the {@link #createTranslation(RasPoint) createTranslation} method + * instead.

+ * @param t the point to be added + * @return the current MInterval + **/ + public RasMInterval translate(RasPoint t) + throws RasDimensionMismatchException, RasResultIsNoIntervalException + { + int i; + + if(dimensionality != t.dimension()) + throw new RasDimensionMismatchException(dimensionality, t.dimension()); + + try { + + for(i=0; i + * This operation is only legal if all lower bounds are + * fixed and the point has the same dimension as the MInterval!

+ * @param t the point to be added + * @return the new MInterval + **/ + public RasMInterval createTranslation(RasPoint t) + throws RasDimensionMismatchException, RasResultIsNoIntervalException + { + if(dimensionality != t.dimension()) + throw new RasDimensionMismatchException(dimensionality, t.dimension()); + + RasMInterval result = new RasMInterval(dimensionality); + + try { + for(int i=0; iNote that this operation modifies the current object. If you want to get a new MInterval, + * use {@link #createUnion(RasMInterval) createUnion} instead.

+ * @param mint1 the first MInterval + * @param mint2 the second MInterval + * @return the current MInterval (representing the union of mint1 and mint2) + **/ + public RasMInterval unionOf(final RasMInterval mint1, final RasMInterval mint2) + throws RasDimensionMismatchException, RasResultIsNoIntervalException + { + if(mint1.dimension() != mint2.dimension()) + throw new RasDimensionMismatchException( mint1.dimension(), mint2.dimension()); + + // cleanup + initializing of this + + dimensionality = mint1.dimension(); + streamInitCnt = dimensionality; + intervals = new RasSInterval[ dimensionality ]; + + try { + + for(int i=0; iNote that this operation modifies the current object. If you want to get a new MInterval, + * use {@link #createUnion(RasMInterval) createUnion} instead.

+ * @param mint the MInterval to be used for the union + * @return the current MInterval (after the union with mint) + **/ + public RasMInterval unionWith(final RasMInterval mint) + throws RasDimensionMismatchException, RasResultIsNoIntervalException + { + if(dimensionality != mint.dimension()) + throw new RasDimensionMismatchException( dimensionality, mint.dimension()); + + try { + + for(int i=0; iNote that this operation modifies the current object. If you want to get a new MInterval, + * use {@link #createDifference(RasMInterval) createDifference} instead.

+ * @param mint1 the first MInterval + * @param mint2 the second MInterval + * @return the current MInterval (representing the difference of mint1 and mint2) + **/ + public RasMInterval differenceOf(final RasMInterval mint1, final RasMInterval mint2) + throws RasDimensionMismatchException, RasResultIsNoIntervalException + { + if(mint1.dimension() != mint2.dimension()) + throw new RasDimensionMismatchException( mint1.dimension(), mint2.dimension()); + + // cleanup + initializing of this + + dimensionality = mint1.dimension(); + streamInitCnt = dimensionality; + intervals = new RasSInterval[ dimensionality ]; + + try { + + for(int i=0; iNote that this operation modifies the current object. If you want to get a new MInterval, + * use {@link #createDifference(RasMInterval) createDifference} instead.

+ * @param mint the MInterval used for building the difference + * @return the current MInterval (representing the difference of this MInterval and mint) + **/ + public RasMInterval differenceWith(final RasMInterval mint) + throws RasDimensionMismatchException, RasResultIsNoIntervalException + { + if(dimensionality != mint.dimension()) + throw new RasDimensionMismatchException(dimensionality, mint.dimension()); + + try { + for(int i=0; iNote that this operation modifies the current object. If you want to get a new MInterval, + * use {@link #createIntersection(RasMInterval) createIntersection} instead.

+ * @param mint1 the first MInterval + * @param mint2 the second MInterval + * @return the current MInterval (representing the intersection of mint1 and mint2) + **/ + public RasMInterval intersectionOf(RasMInterval mint1, RasMInterval mint2) + throws RasDimensionMismatchException, RasResultIsNoIntervalException + { + if(mint1.dimension() != mint2.dimension()) + throw new RasDimensionMismatchException( mint1.dimension(), mint2.dimension()); + + // cleanup + initializing of this + + dimensionality = mint1.dimension(); + streamInitCnt = dimensionality; + intervals = new RasSInterval[ dimensionality ]; + + try { + for(int i=0; iNote that this operation modifies the current object. If you want to get a new MInterval, + * use {@link #createIntersection(RasMInterval) createIntersection} instead.

+ * @param mint the MInterval used for building the intersection + * @return the current MInterval (representing the intersection of this MInterval and mint) + **/ + public RasMInterval intersectionWith(RasMInterval mint) + throws RasDimensionMismatchException, RasResultIsNoIntervalException + { + if(dimensionality != mint.dimension()) + throw new RasDimensionMismatchException(dimensionality, mint.dimension()); + + try { + for(int i=0; iNote that this operation modifies the current object. If you want to get a new MInterval, + * use {@link #createClosure(RasMInterval) createClosure} instead.

+ * @param mint1 the first MInterval + * @param mint2 the second MInterval + * @return the current MInterval (representing the closure of mint1 and mint2) + **/ + public RasMInterval closureOf(RasMInterval mint1, RasMInterval mint2) + throws RasDimensionMismatchException, RasResultIsNoIntervalException + { + + if(mint1.dimension() != mint2.dimension()) + throw new RasDimensionMismatchException( mint1.dimension(), mint2.dimension()); + + // cleanup + initializing of this + + dimensionality = mint1.dimension(); + streamInitCnt = dimensionality; + intervals = new RasSInterval[ dimensionality ]; + + try + { + for(int i=0; iNote that this operation modifies the current object. If you want to get a new MInterval, + * use {@link #createClosure(RasMInterval) createClosure} instead.

+ * @param mint the MInterval used for building the closure + * @return the current MInterval (representing the closure of this MInterval and mint) + **/ + public RasMInterval closureWith(final RasMInterval mint) + throws RasDimensionMismatchException, RasResultIsNoIntervalException + { + if(dimensionality != mint.dimension()) + throw new RasDimensionMismatchException( dimensionality, mint.dimension()); + + try + { + for(int i=0; i intervals[i].high()) + throw new RasIndexOutOfBoundsException(intervals[i].low(), intervals[i].high(), point.item(i) ); + + offset = (offset + point.item(i) - intervals[i].low()) * (intervals[i+1].high() - intervals[i+1].low() + 1); + } + + // now i = dimensionality - 1 + if(point.item(i) < intervals[i].low() || point.item(i) > intervals[i].high()) + throw new RasIndexOutOfBoundsException(intervals[i].low(), intervals[i].high(), point.item(i) ); + + offset += point.item(i) - intervals[i].low(); + + return offset; + } + + /** + * This method calculates the spatial domain + * coordinates as a point from the offset + * specified. Lower dimensions are higher + * valued which means that the highest dimension + * is stored in a sequence. + **/ + RasPoint cellPoint(long offset) throws RasResultIsNoCellException + { + int i; + long factor=1; + RasPoint pt = new RasPoint(dimensionality); + + try { + + if(offset >= cellCount()) + throw new RasResultIsNoCellException(); + + for(i=0; i= dimensionality) + throw new RasIndexOutOfBoundsException(0, dimensionality-1, dim); + + dimensionality -= 1; + streamInitCnt = dimensionality; + RasSInterval[] newIntervals = new RasSInterval[ dimensionality ]; + + for(int i=0, j=0; i 0) + sz += dimensionality * 18; + + return sz; + } + + /** gives back the string representation */ + public String toString() + { + String retString = ""; + if(dimensionality > 0) + { + for(int i=0; i
-1 if the point has not the same dimensionality
1 if the point is covered by this MInterval
0 if the point is not covered