KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > sleepycat > persist > impl > ObjectArrayFormat


1 /*-
2  * See the file LICENSE for redistribution information.
3  *
4  * Copyright (c) 2002,2006 Oracle. All rights reserved.
5  *
6  * $Id: ObjectArrayFormat.java,v 1.23 2006/10/30 21:14:32 bostic Exp $
7  */

8
9 package com.sleepycat.persist.impl;
10
11 import java.lang.reflect.Array JavaDoc;
12 import java.util.IdentityHashMap JavaDoc;
13 import java.util.Map JavaDoc;
14 import java.util.Set JavaDoc;
15
16 import com.sleepycat.je.DatabaseEntry;
17 import com.sleepycat.persist.raw.RawObject;
18
19 /**
20  * An array of objects having a specified number of dimensions. All
21  * multidimensional arrays are handled by this class, since even a primitive
22  * array of more than one dimension is an array of objects, where the component
23  * objects may be primitive arrays. The {@link PrimitiveArrayFormat} class
24  * handles primitive arrays of one dimension only.
25  *
26  * In this class, and {@link PrimitiveArrayFormat}, we resort to using
27  * reflection to allocate multidimensional arrays. If there is a need for it,
28  * reflection could be avoided in the future by generating code as new array
29  * formats are encountered.
30  *
31  * @author Mark Hayes
32  */

33 public class ObjectArrayFormat extends Format {
34
35     private static final long serialVersionUID = 4317004346690441892L;
36
37     private Format componentFormat;
38     private int nDimensions;
39     private transient Format useComponentFormat;
40
41     ObjectArrayFormat(Class JavaDoc type) {
42         super(type);
43         String JavaDoc name = getClassName();
44         for (nDimensions = 0;
45              name.charAt(nDimensions) == '[';
46              nDimensions += 1) {
47         }
48     }
49
50     @Override JavaDoc
51     public boolean isArray() {
52         return true;
53     }
54
55     @Override JavaDoc
56     public int getDimensions() {
57         return nDimensions;
58     }
59
60     @Override JavaDoc
61     public Format getComponentType() {
62         return (useComponentFormat != null) ?
63             useComponentFormat : componentFormat ;
64     }
65
66     @Override JavaDoc
67     void collectRelatedFormats(Catalog catalog,
68                                Map JavaDoc<String JavaDoc,Format> newFormats) {
69         Class JavaDoc cls = getType().getComponentType();
70         catalog.createFormat(cls, newFormats);
71     }
72
73     @Override JavaDoc
74     void initialize(Catalog catalog) {
75         /* Set the component format for a new (never initialized) format. */
76         if (componentFormat == null) {
77             Class JavaDoc cls = getType().getComponentType();
78             componentFormat = catalog.getFormat(cls.getName());
79         }
80         useComponentFormat = componentFormat.getLatestVersion();
81     }
82
83     @Override JavaDoc
84     boolean isAssignableTo(Format format) {
85         if (super.isAssignableTo(format)) {
86             return true;
87         }
88         if (format instanceof ObjectArrayFormat) {
89             ObjectArrayFormat other = (ObjectArrayFormat) format;
90             if (useComponentFormat.isAssignableTo(other.useComponentFormat)) {
91                 return true;
92             }
93         }
94         return false;
95     }
96
97     @Override JavaDoc
98     Object JavaDoc newArray(int len) {
99         return Array.newInstance(getType(), len);
100     }
101
102     @Override JavaDoc
103     public Object JavaDoc newInstance(EntityInput input, boolean rawAccess) {
104         int len = input.readArrayLength();
105         if (rawAccess) {
106             return new RawObject(this, new Object JavaDoc[len]);
107         } else {
108             return useComponentFormat.newArray(len);
109         }
110     }
111
112     @Override JavaDoc
113     public Object JavaDoc readObject(Object JavaDoc o, EntityInput input, boolean rawAccess) {
114         Object JavaDoc[] a;
115         if (rawAccess) {
116             a = ((RawObject) o).getElements();
117         } else {
118             a = (Object JavaDoc[]) o;
119         }
120         for (int i = 0; i < a.length; i += 1) {
121             a[i] = input.readObject();
122         }
123         return o;
124     }
125
126     @Override JavaDoc
127     void writeObject(Object JavaDoc o, EntityOutput output, boolean rawAccess) {
128         Object JavaDoc[] a;
129         if (rawAccess) {
130             a = ((RawObject) o).getElements();
131         } else {
132             a = (Object JavaDoc[]) o;
133         }
134         output.writeArrayLength(a.length);
135         for (int i = 0; i < a.length; i += 1) {
136             output.writeObject(a[i], useComponentFormat);
137         }
138     }
139
140     @Override JavaDoc
141     Object JavaDoc convertRawObject(Catalog catalog,
142                             boolean rawAccess,
143                             RawObject rawObject,
144                             IdentityHashMap JavaDoc converted) {
145         RawArrayInput input = new RawArrayInput
146             (catalog, rawAccess, converted, rawObject, useComponentFormat);
147         Object JavaDoc a = newInstance(input, rawAccess);
148         converted.put(rawObject, a);
149         return readObject(a, input, rawAccess);
150     }
151
152     @Override JavaDoc
153     void skipContents(RecordInput input) {
154         int len = input.readPackedInt();
155         for (int i = 0; i < len; i += 1) {
156             input.skipField(useComponentFormat);
157         }
158     }
159
160     @Override JavaDoc
161     void copySecMultiKey(RecordInput input, Format keyFormat, Set JavaDoc results) {
162         int len = input.readPackedInt();
163         for (int i = 0; i < len; i += 1) {
164             KeyLocation loc = input.getKeyLocation(useComponentFormat);
165             if (loc == null) {
166                 throw new IllegalArgumentException JavaDoc
167                     ("Secondary key values in array may not be null");
168             }
169             if (loc.format != useComponentFormat) {
170                 throw new IllegalStateException JavaDoc
171                     (useComponentFormat.getClassName());
172             }
173             int off1 = loc.input.getBufferOffset();
174             useComponentFormat.skipContents(loc.input);
175             int off2 = loc.input.getBufferOffset();
176             DatabaseEntry entry = new DatabaseEntry
177                 (loc.input.getBufferBytes(), off1, off2 - off1);
178             results.add(entry);
179         }
180     }
181
182     @Override JavaDoc
183     boolean evolve(Format newFormat, Evolver evolver) {
184
185         /*
186          * When the class name of the component changes, we need a new format
187          * that references it. Otherwise, don't propogate changes from
188          * components upward to their arrays.
189          */

190         Format latest = componentFormat.getLatestVersion();
191         if (latest != componentFormat &&
192             !latest.getClassName().equals(componentFormat.getClassName())) {
193             evolver.useEvolvedFormat(this, newFormat, newFormat);
194         } else {
195             evolver.useOldFormat(this, newFormat);
196         }
197         return true;
198     }
199 }
200
Popular Tags