/* * Copyright (c) 2012 Data Harmonisation Panel * * All rights reserved. This program and the accompanying materials are made * available under the terms of the GNU Lesser General Public License as * published by the Free Software Foundation, either version 3 of the License, * or (at your option) any later version. * * You should have received a copy of the GNU Lesser General Public License * along with this distribution. If not, see <http://www.gnu.org/licenses/>. * * Contributors: * HUMBOLDT EU Integrated Project #030962 * Data Harmonisation Panel <http://www.dhpanel.eu> */ package eu.esdihumboldt.hale.common.schema.model.constraint.property; import net.jcip.annotations.Immutable; import eu.esdihumboldt.hale.common.schema.model.Constraint; import eu.esdihumboldt.hale.common.schema.model.GroupPropertyConstraint; import eu.esdihumboldt.hale.common.schema.model.PropertyConstraint; /** * Specifies the cardinality for a property, default is for a property to occur * exactly once. * * @author Simon Templer */ @Immutable @Constraint(mutable = false) public class Cardinality implements GroupPropertyConstraint, PropertyConstraint { /** * Value for unrestricted {@link #maxOccurs} */ public static final long UNBOUNDED = -1; /** * Cardinality constraint for properties that occur exactly once (one) */ public static final Cardinality CC_EXACTLY_ONCE = new Cardinality(1, 1); /** * Cardinality constraint for properties that occur once or not at all (zero * to one) */ public static final Cardinality CC_OPTIONAL = new Cardinality(0, 1); /** * Cardinality constraint for properties that occur at least once (one to * infinity) */ public static final Cardinality CC_AT_LEAST_ONCE = new Cardinality(1, UNBOUNDED); /** * Cardinality constraint for properties that occur in any number (zero to * infinity) */ public static final Cardinality CC_ANY_NUMBER = new Cardinality(0, UNBOUNDED); /** * Get the cardinality constraint with the given occurrences * * @param minOccurs the number of minimum occurrences of a property, may not * be negative * @param maxOccurs the number of maximum occurrences of a property, * {@value #UNBOUNDED} for an infinite maximum occurrence * @return the cardinality constraint */ public static Cardinality get(long minOccurs, long maxOccurs) { // use singletons if possible if (minOccurs == 0) { if (maxOccurs == 1) { return CC_OPTIONAL; } else if (maxOccurs == UNBOUNDED) { return CC_ANY_NUMBER; } } else if (minOccurs == 1) { if (maxOccurs == 1) { return CC_EXACTLY_ONCE; } else if (maxOccurs == UNBOUNDED) { return CC_AT_LEAST_ONCE; } } return new Cardinality(minOccurs, maxOccurs); } /** * The number of minimum occurrences of a property */ private final long minOccurs; /** * The number of maximum occurrences of a property */ private final long maxOccurs; /** * Creates a default cardinality constraint with {@link #minOccurs} and * {@link #maxOccurs} one.<br> * <br> * NOTE: Instead of using the constructor to create new instances please use * {@link #get(long, long)} if possible. */ public Cardinality() { this(1, 1); } /** * Create a cardinality constraint.<br> * <br> * NOTE: Instead of using the constructor to create new instances please use * {@link #get(long, long)} if possible. * * @param minOccurs the number of minimum occurrences of a property, may not * be negative * @param maxOccurs the number of maximum occurrences of a property, * {@value #UNBOUNDED} for an infinite maximum occurrence */ private Cardinality(long minOccurs, long maxOccurs) { super(); this.minOccurs = minOccurs; this.maxOccurs = maxOccurs; } /** * Get the number of minimum occurrences of a property * * @return the number of minimum occurrences of a property */ public long getMinOccurs() { return minOccurs; } /** * Get the number of maximum occurrences of a property * * @return the number of maximum occurrences of a property */ public long getMaxOccurs() { return maxOccurs; } /** * @return if the property may occur more than once */ public boolean mayOccurMultipleTimes() { return getMaxOccurs() == UNBOUNDED || getMaxOccurs() > 1; } @Override public String toString() { return getMinOccurs() + ".." + ((getMaxOccurs() == UNBOUNDED) ? ('n') : (getMaxOccurs())); } @Override public int hashCode() { final int prime = 31; int result = 1; result = prime * result + (int) (maxOccurs ^ (maxOccurs >>> 32)); result = prime * result + (int) (minOccurs ^ (minOccurs >>> 32)); return result; } @Override public boolean equals(Object obj) { if (this == obj) return true; if (obj == null) return false; if (getClass() != obj.getClass()) return false; Cardinality other = (Cardinality) obj; if (maxOccurs != other.maxOccurs) return false; if (minOccurs != other.minOccurs) return false; return true; } }