//
// QuantityDimension.java
//

/*
 VisAD system for interactive analysis and visualization of numerical
 data.  Copyright (C) 1996 - 2017 Bill Hibbard, Curtis Rueden, Tom
 Rink, Dave Glowacki, Steve Emmerson, Tom Whittaker, Don Murray, and
 Tommy Jasmin.

 This library is free software; you can redistribute it and/or
 modify it under the terms of the GNU Library General Public
 License as published by the Free Software Foundation; either
 version 2 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
 Library General Public License for more details.

 You should have received a copy of the GNU Library General Public
 License along with this library; if not, write to the Free
 Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
 MA 02111-1307, USA
 */

package visad;

import java.io.Serializable;

/**
 * This class represents the dimension of a quantity. For example, consider a
 * nonrelativistic particle of mass m in uniform motion which travels
 * a distance l in a time t. Its velocity is
 * v=l/t and its kinetic energy is
 * E=mv2/2=ml2t-2/2. The dimension
 * of E is dim E=ML2T-2 and the
 * dimensional exponents are 1, 2, and -2.
 * 
 * A QuantityDimension is immutable.
 */
public final class QuantityDimension implements Serializable, Comparable {
	/**
	 * The dimensional exponents.
	 */
	private/* final */byte[]	exponents;

	/**
	 * Constructs from nothing (i.e. constructs a dimensionless quantity).
	 */
	public QuantityDimension() {
		initialize(0);
	}

	/**
	 * Constructs from another dimension of a quantity.
	 */
	public QuantityDimension(final QuantityDimension that) {
		initialize(that.exponents.length);

		System
				.arraycopy(that.exponents, 0, exponents, 0,
						that.exponents.length);
	}

	/**
	 * Constructs from an existing Unit.
	 */
	public QuantityDimension(final Unit unit) throws UnitException {
		initialize(unit.getDerivedUnit());
	}

	/**
	 * Initialize from a number of base quantities. Private to ensure use of the
	 * public constructors and the concomitant setting of the dimensional
	 * exponents.
	 */
	private void initialize(final int n) {
		exponents = new byte[n];
	}

	/**
	 * Initialize from a DerivedUnit.
	 */
	private void initialize(final DerivedUnit unit) throws UnitException {
		initialize(BaseQuantity.size());

		for (int i = 0; i < unit.factors.length; ++i) {
			final String name = unit.factors[i].baseUnit.quantityName();
			final BaseQuantity baseQuantity = BaseQuantity.get(name);

			if (baseQuantity == null) {
				throw new UnitException("No base quantity for \"" + name + "\"");
			}

			exponents[baseQuantity.getIndex()] = (byte) unit.factors[i].power;
		}
	}

	/**
	 * Compare this dimension of a quantity to another.
	 */
	public int compareTo(final Object obj) {
		final QuantityDimension that = (QuantityDimension) obj;

		return isShorterThan(that)
				? compare(this, that)
				: -compare(that, this);
	}

	/**
	 * Indicate whether or not this dimension of a quantity is shorter or equal
	 * to another.
	 */
	private boolean isShorterThan(final QuantityDimension that) {
		return exponents.length < that.exponents.length;
	}

	/**
	 * Compare a shorter dimensional quantity to a longer one.
	 * 
	 * @precondition shorter.exponents.length <=
	 * 			longer.exponents.length.
	 */
	private static int compare(final QuantityDimension shorter,
			final QuantityDimension longer) {
		int n = 0;

		for (int i = 0; n == 0 && i < shorter.exponents.length; ++i) {
			n = shorter.exponents[i] - longer.exponents[i];
		}

		for (int i = shorter.exponents.length; n == 0
				&& i < longer.exponents.length; ++i) {
			n = -longer.exponents[i];
		}

		return n;
	}

	/**
	 * Indicate whether or not this dimension of a quantity is the same as
	 * another.
	 */
	@Override
	public boolean equals(final Object obj) {
		return compareTo(obj) == 0;
	}

	/**
	 * Raise this dimension of a quantity by a power.
	 */
	public QuantityDimension raise(final int power) {
		final QuantityDimension newDimension = new QuantityDimension(this);

		for (int i = 0; i < newDimension.exponents.length; ++i) {
			newDimension.exponents[i] *= power;
		}

		return newDimension;
	}

	/**
	 * Multiply this dimension of a quantity by another.
	 */
	public QuantityDimension multiply(final QuantityDimension that) {
		return isShorterThan(that)
				? multiply(this, that)
				: multiply(that, this);
	}

	/**
	 * Multiply a shorter dimension of a quantity by a longer one.
	 */
	private static QuantityDimension multiply(final QuantityDimension shorter,
			final QuantityDimension longer) {
		final QuantityDimension newDimension = new QuantityDimension(longer);

		for (int i = 0; i < shorter.exponents.length; ++i) {
			newDimension.exponents[i] += shorter.exponents[i];
		}

		return newDimension;
	}

	/**
	 * Divide this dimension of a quantity by another.
	 */
	public QuantityDimension divide(final QuantityDimension that) {
		return multiply(that.raise(-1));
	}

	/**
	 * Indicate whether or not this dimension of a quantity is dimensionless.
	 */
	public boolean isDimensionless() {
		for (int i = 0; i < exponents.length; ++i) {
			if (exponents[i] != 0) {
				return false;
			}
		}

		return true;
	}

	/**
	 * Return a string representation of this dimension of a quantity.
	 */
	@Override
	public String toString() {
		String rep;

		if (isDimensionless()) {
			rep = "1"; // dimensionless quantity
		}
		else {
			final StringBuffer buf = new StringBuffer(128);

			for (int i = 0; i < exponents.length; ++i) {
				final int exponent = exponents[i];

				if (exponent != 0) {
					if (buf.length() > 0) {
						buf.append(" ");
					}

					buf.append("(");
					buf.append(BaseQuantity.get(i).getName());
					buf.append(")");

					if (exponent != 1) {
						buf.append("^");
						buf.append(exponent);
					}
				}
			}

			rep = buf.toString();
		}

		return rep;
	}

	/**
	 * Test this class.
	 */
	// /*
	public static void main(final String[] args) {
		final QuantityDimension dim1 = new QuantityDimension();

		dim1.exponents[0] = -3;
		dim1.exponents[1] = -2;
		dim1.exponents[2] = -1;
		dim1.exponents[3] = 0;
		dim1.exponents[4] = 1;
		dim1.exponents[5] = 2;
		dim1.exponents[6] = 3;
		dim1.exponents[7] = 4;

		System.out.println("dim1=(" + dim1 + ")");
		System.out.println("dim1.equals(dim1)=" + dim1.equals(dim1));
		System.out.println("dim1.compareTo(dim1)=" + dim1.compareTo(dim1));

		final QuantityDimension dim2 = new QuantityDimension();

		dim2.exponents[0] = -3;
		dim2.exponents[1] = -2;
		dim2.exponents[2] = -1;
		dim2.exponents[3] = 1;
		dim2.exponents[4] = 1;
		dim2.exponents[5] = 2;
		dim2.exponents[6] = 3;
		dim2.exponents[7] = 4;

		System.out.println("dim2=(" + dim2 + ")");
		System.out.println("dim1.equals(dim2)=" + dim1.equals(dim2));
		System.out.println("dim1.compareTo(dim2)=" + dim1.compareTo(dim2));
	}
	// */
}

 

Ads help maintain this website.