Frames | No Frames |
1: /* TabularType.java -- Type descriptor for TabularData instances. 2: Copyright (C) 2006, 2007 Free Software Foundation, Inc. 3: 4: This file is part of GNU Classpath. 5: 6: GNU Classpath is free software; you can redistribute it and/or modify 7: it under the terms of the GNU General Public License as published by 8: the Free Software Foundation; either version 2, or (at your option) 9: any later version. 10: 11: GNU Classpath is distributed in the hope that it will be useful, but 12: WITHOUT ANY WARRANTY; without even the implied warranty of 13: MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 14: General Public License for more details. 15: 16: You should have received a copy of the GNU General Public License 17: along with GNU Classpath; see the file COPYING. If not, write to the 18: Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 19: 02110-1301 USA. 20: 21: Linking this library statically or dynamically with other modules is 22: making a combined work based on this library. Thus, the terms and 23: conditions of the GNU General Public License cover the whole 24: combination. 25: 26: As a special exception, the copyright holders of this library give you 27: permission to link this library with independent modules to produce an 28: executable, regardless of the license terms of these independent 29: modules, and to copy and distribute the resulting executable under 30: terms of your choice, provided that you also meet, for each linked 31: independent module, the terms and conditions of the license of that 32: module. An independent module is a module which is not derived from 33: or based on this library. If you modify this library, you may extend 34: this exception to your version of the library, but you are not 35: obligated to do so. If you do not wish to do so, delete this 36: exception statement from your version. */ 37: 38: package javax.management.openmbean; 39: 40: import java.util.Arrays; 41: import java.util.Collections; 42: import java.util.Iterator; 43: import java.util.List; 44: 45: /** 46: * The open type descriptor for instances of the 47: * {@link TabularData} class. 48: * 49: * @author Andrew John Hughes (gnu_andrew@member.fsf.org) 50: * @since 1.5 51: */ 52: public class TabularType 53: extends OpenType<TabularData> 54: { 55: 56: /** 57: * Compatible with JDK 1.5 58: */ 59: private static final long serialVersionUID = 6554071860220659261L; 60: 61: /** 62: * The composite type used by the rows of the table. 63: */ 64: private CompositeType rowType; 65: 66: /** 67: * The list of index names, which form the columns of the table. 68: * They are retained in the order given by the user, and is 69: * unmodifiable. 70: */ 71: private List<String> indexNames; 72: 73: /** 74: * The hash code of this instance. 75: */ 76: private transient Integer hashCode; 77: 78: /** 79: * The <code>toString()</code> result of this instance. 80: */ 81: private transient String string; 82: 83: /** 84: * <p> 85: * Constructs a new {@link TabularType} instance for the given 86: * type name, description, row type and index names. All parameters 87: * (including the individual elements of the array of index names) 88: * must be non-null and those that are of type {@link java.lang.String} 89: * must be non-empty. The array of index names must also be non-empty. 90: * </p> 91: * <p> 92: * The result of <code>TabularData.class.getName()</code> is adopted 93: * as the class name (see {@link OpenType}). The ordering of the array 94: * elements is relevant in determining the indicies of the values in the 95: * table, and thus in the use of the 96: * {@link TabularData#get(java.lang.Object[])} and 97: * {@link TabularData#remove(java.lang.Object[])} methods of the 98: * {@link TabularData} class. 99: * </p> 100: * 101: * @param name the name of this tabular type. 102: * @param desc a description of this tabular type. 103: * @param rowType the type of the rows of the table. 104: * @param indexNames the names used to index the rows within the table. 105: * @throws IllegalArgumentException if any validity constraint listed above 106: * is broken. 107: * @throws OpenDataException if an index name does not match a corresponding 108: * name in the given row type. 109: */ 110: public TabularType(String name, String desc, CompositeType rowType, 111: String[] indexNames) 112: throws OpenDataException 113: { 114: super(TabularData.class.getName(), name, desc); 115: if (rowType == null) 116: throw new IllegalArgumentException("A null row type was given."); 117: for (int a = 0; a < indexNames.length; ++a) 118: { 119: if (indexNames[a] == null) 120: throw new IllegalArgumentException("Name " + a + 121: " is null."); 122: if (indexNames[a].length() == 0) 123: throw new IllegalArgumentException("Name " + a + 124: " is the empty string."); 125: if (!(rowType.containsKey(indexNames[a]))) 126: throw new OpenDataException("No matching key for " + 127: indexNames[a] + " was found in " + 128: "the supplied row type."); 129: } 130: this.rowType = rowType; 131: this.indexNames = Collections.unmodifiableList(Arrays.asList(indexNames)); 132: } 133: 134: /** 135: * <p> 136: * Compares this tabular data type with another object 137: * for equality. The objects are judged to be equal if: 138: * </p> 139: * <ul> 140: * <li><code>obj</code> is not null.</li> 141: * <li><code>obj</code> is an instance of 142: * {@link TabularType}.</li> 143: * <li>The type names are equal.</li> 144: * <li>The row types are equal.</li> 145: * <li>The index names are equal and in the same order.</li> 146: * </ul> 147: * 148: * @param obj the object to compare with. 149: * @return true if the conditions above hold. 150: */ 151: public boolean equals(Object obj) 152: { 153: if (!(obj instanceof TabularType)) 154: return false; 155: TabularType ttype = (TabularType) obj; 156: return (ttype.getTypeName().equals(getTypeName()) 157: && (ttype.getRowType().equals(getRowType())) 158: && (ttype.getIndexNames().equals(getIndexNames()))); 159: } 160: 161: /** 162: * Returns an unmodifiable list containing the index names. 163: * The ordering of these names is used to determine the indicies 164: * of the {@link CompositeData} values, and is retained from that 165: * used in the call to this object's constructor. 166: * 167: * @return an unmodifiable list of the index names used by this 168: * tabular data structure. 169: */ 170: public List<String> getIndexNames() 171: { 172: return indexNames; 173: } 174: 175: /** 176: * Returns the type of the rows used by this tabular data structure. 177: * 178: * @return the row type. 179: */ 180: public CompositeType getRowType() 181: { 182: return rowType; 183: } 184: 185: /** 186: * <p> 187: * Returns the hash code of the tabular data type. 188: * This is computed as the sum of the hash codes of the 189: * index names together with the hash code of the type 190: * name and row type. These are the same elements 191: * of the type that are compared as part of the 192: * {@link #equals(java.lang.Object)} method, thus ensuring 193: * that the hashcode is compatible with the equality 194: * test. 195: * </p> 196: * <p> 197: * As instances of this class are immutable, the hash code 198: * is computed just once for each instance and reused 199: * throughout its life. 200: * </p> 201: * 202: * @return the hash code of this instance. 203: */ 204: public int hashCode() 205: { 206: if (hashCode == null) 207: { 208: int elementTotal = 0; 209: for (String s : indexNames) 210: elementTotal += s.hashCode(); 211: hashCode = Integer.valueOf(elementTotal 212: + getTypeName().hashCode() 213: + rowType.hashCode()); 214: } 215: return hashCode.intValue(); 216: } 217: 218: /** 219: * Returns true if the specified object is a member of this 220: * tabular type. The object is judged to be so if it is 221: * an instance of {@link TabularData} with an equivalent 222: * type, according to the definition of 223: * {@link #equals(java.lang.Object)} for {@link TabularType}. 224: * 225: * @param obj the object to test for membership. 226: * @return true if the object is a member of this type. 227: */ 228: public boolean isValue(Object obj) 229: { 230: if (obj instanceof TabularData) 231: { 232: TabularData data = (TabularData) obj; 233: return equals(data.getTabularType()); 234: } 235: return false; 236: } 237: 238: /** 239: * <p> 240: * Returns a textual representation of this instance. This 241: * is constructed using the class name 242: * (<code>javax.management.openmbean.TabularType</code>) 243: * and each element of the instance which is relevant to 244: * the definition of {@link equals(java.lang.Object)} and 245: * {@link hashCode()} (i.e. the type name, the row type 246: * and the index names). 247: * </p> 248: * <p> 249: * As instances of this class are immutable, the return value 250: * is computed just once for each instance and reused 251: * throughout its life. 252: * </p> 253: * 254: * @return a @link{java.lang.String} instance representing 255: * the instance in textual form. 256: */ 257: public String toString() 258: { 259: if (string == null) 260: string = getClass().getName() 261: + "[name=" + getTypeName() 262: + ", rowType=" + rowType 263: + ", indexNames=" + indexNames 264: + "]"; 265: return string; 266: } 267: 268: }