KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > eclipse > jdt > internal > core > search > matching > ConstructorPattern


1 /*******************************************************************************
2  * Copyright (c) 2000, 2006 IBM Corporation and others.
3  * All rights reserved. This program and the accompanying materials
4  * are made available under the terms of the Eclipse Public License v1.0
5  * which accompanies this distribution, and is available at
6  * http://www.eclipse.org/legal/epl-v10.html
7  *
8  * Contributors:
9  * IBM Corporation - initial API and implementation
10  *******************************************************************************/

11 package org.eclipse.jdt.internal.core.search.matching;
12
13 import java.io.IOException JavaDoc;
14
15 import org.eclipse.jdt.core.BindingKey;
16 import org.eclipse.jdt.core.Flags;
17 import org.eclipse.jdt.core.IMethod;
18 import org.eclipse.jdt.core.JavaModelException;
19 import org.eclipse.jdt.core.compiler.CharOperation;
20 import org.eclipse.jdt.core.search.SearchPattern;
21 import org.eclipse.jdt.internal.core.index.EntryResult;
22 import org.eclipse.jdt.internal.core.index.Index;
23 import org.eclipse.jdt.internal.core.util.Util;
24
25 public class ConstructorPattern extends JavaSearchPattern {
26
27 protected boolean findDeclarations;
28 protected boolean findReferences;
29
30 public char[] declaringQualification;
31 public char[] declaringSimpleName;
32
33 public char[][] parameterQualifications;
34 public char[][] parameterSimpleNames;
35 public int parameterCount;
36 public boolean varargs = false;
37
38 // Signatures and arguments for generic search
39
char[][][] parametersTypeSignatures;
40 char[][][][] parametersTypeArguments;
41 boolean constructorParameters = false;
42 char[][] constructorArguments;
43
44 protected static char[][] REF_CATEGORIES = { CONSTRUCTOR_REF };
45 protected static char[][] REF_AND_DECL_CATEGORIES = { CONSTRUCTOR_REF, CONSTRUCTOR_DECL };
46 protected static char[][] DECL_CATEGORIES = { CONSTRUCTOR_DECL };
47
48 /**
49  * Constructor entries are encoded as TypeName '/' Arity:
50  * e.g. 'X/0'
51  */

52 public static char[] createIndexKey(char[] typeName, int argCount) {
53     char[] countChars = argCount < 10
54         ? COUNTS[argCount]
55         : ("/" + String.valueOf(argCount)).toCharArray(); //$NON-NLS-1$
56
return CharOperation.concat(typeName, countChars);
57 }
58
59 ConstructorPattern(int matchRule) {
60     super(CONSTRUCTOR_PATTERN, matchRule);
61 }
62 public ConstructorPattern(
63     boolean findDeclarations,
64     boolean findReferences,
65     char[] declaringSimpleName,
66     char[] declaringQualification,
67     char[][] parameterQualifications,
68     char[][] parameterSimpleNames,
69     int matchRule) {
70
71     this(matchRule);
72
73     this.findDeclarations = findDeclarations;
74     this.findReferences = findReferences;
75
76     this.declaringQualification = isCaseSensitive() ? declaringQualification : CharOperation.toLowerCase(declaringQualification);
77     this.declaringSimpleName = (isCaseSensitive() || isCamelCase()) ? declaringSimpleName : CharOperation.toLowerCase(declaringSimpleName);
78     if (parameterSimpleNames != null) {
79         this.parameterCount = parameterSimpleNames.length;
80         boolean synthetic = this.parameterCount>0 && declaringQualification != null && CharOperation.equals(CharOperation.concat(parameterQualifications[0], parameterSimpleNames[0], '.'), declaringQualification);
81         int offset = 0;
82         if (synthetic) {
83             // skip first synthetic parameter
84
this.parameterCount--;
85             offset++;
86         }
87         this.parameterQualifications = new char[this.parameterCount][];
88         this.parameterSimpleNames = new char[this.parameterCount][];
89         for (int i = 0; i < this.parameterCount; i++) {
90             this.parameterQualifications[i] = isCaseSensitive() ? parameterQualifications[i+offset] : CharOperation.toLowerCase(parameterQualifications[i+offset]);
91             this.parameterSimpleNames[i] = isCaseSensitive() ? parameterSimpleNames[i+offset] : CharOperation.toLowerCase(parameterSimpleNames[i+offset]);
92         }
93     } else {
94         this.parameterCount = -1;
95     }
96     ((InternalSearchPattern)this).mustResolve = mustResolve();
97 }
98 /*
99  * Instanciate a method pattern with signatures for generics search
100  */

101 public ConstructorPattern(
102     boolean findDeclarations,
103     boolean findReferences,
104     char[] declaringSimpleName,
105     char[] declaringQualification,
106     char[][] parameterQualifications,
107     char[][] parameterSimpleNames,
108     String JavaDoc[] parameterSignatures,
109     IMethod method,
110 // boolean varargs,
111
int matchRule) {
112
113     this(findDeclarations,
114         findReferences,
115         declaringSimpleName,
116         declaringQualification,
117         parameterQualifications,
118         parameterSimpleNames,
119         matchRule);
120
121     // Set flags
122
try {
123         this.varargs = (method.getFlags() & Flags.AccVarargs) != 0;
124     } catch (JavaModelException e) {
125         // do nothing
126
}
127
128     // Get unique key for parameterized constructors
129
String JavaDoc genericDeclaringTypeSignature = null;
130     String JavaDoc key;
131     if (method.isResolved() && new BindingKey(key = method.getKey()).isParameterizedType()) {
132         genericDeclaringTypeSignature = Util.getDeclaringTypeSignature(key);
133     } else {
134         constructorParameters = true;
135     }
136
137     // Store type signature and arguments for declaring type
138
if (genericDeclaringTypeSignature != null) {
139         this.typeSignatures = Util.splitTypeLevelsSignature(genericDeclaringTypeSignature);
140         setTypeArguments(Util.getAllTypeArguments(this.typeSignatures));
141     } else {
142         storeTypeSignaturesAndArguments(method.getDeclaringType());
143     }
144
145     // store type signatures and arguments for method parameters type
146
if (parameterSignatures != null) {
147         int length = parameterSignatures.length;
148         if (length > 0) {
149             parametersTypeSignatures = new char[length][][];
150             parametersTypeArguments = new char[length][][][];
151             for (int i=0; i<length; i++) {
152                 parametersTypeSignatures[i] = Util.splitTypeLevelsSignature(parameterSignatures[i]);
153                 parametersTypeArguments[i] = Util.getAllTypeArguments(parametersTypeSignatures[i]);
154             }
155         }
156     }
157
158     // Store type signatures and arguments for method
159
constructorArguments = extractMethodArguments(method);
160     if (hasConstructorArguments()) ((InternalSearchPattern)this).mustResolve = true;
161 }
162 /*
163  * Instanciate a method pattern with signatures for generics search
164  */

165 public ConstructorPattern(
166     boolean findDeclarations,
167     boolean findReferences,
168     char[] declaringSimpleName,
169     char[] declaringQualification,
170     String JavaDoc declaringSignature,
171     char[][] parameterQualifications,
172     char[][] parameterSimpleNames,
173     String JavaDoc[] parameterSignatures,
174     char[][] arguments,
175     int matchRule) {
176
177     this(findDeclarations,
178         findReferences,
179         declaringSimpleName,
180         declaringQualification,
181         parameterQualifications,
182         parameterSimpleNames,
183         matchRule);
184
185     // Store type signature and arguments for declaring type
186
if (declaringSignature != null) {
187         typeSignatures = Util.splitTypeLevelsSignature(declaringSignature);
188         setTypeArguments(Util.getAllTypeArguments(typeSignatures));
189     }
190
191     // Store type signatures and arguments for method parameters type
192
if (parameterSignatures != null) {
193         int length = parameterSignatures.length;
194         if (length > 0) {
195             parametersTypeSignatures = new char[length][][];
196             parametersTypeArguments = new char[length][][][];
197             for (int i=0; i<length; i++) {
198                 parametersTypeSignatures[i] = Util.splitTypeLevelsSignature(parameterSignatures[i]);
199                 parametersTypeArguments[i] = Util.getAllTypeArguments(parametersTypeSignatures[i]);
200             }
201         }
202     }
203
204     // Store type signatures and arguments for method
205
constructorArguments = arguments;
206     if (arguments == null || arguments.length == 0) {
207         if (getTypeArguments() != null && getTypeArguments().length > 0) {
208             constructorArguments = getTypeArguments()[0];
209         }
210     }
211     if (hasConstructorArguments()) ((InternalSearchPattern)this).mustResolve = true;
212 }
213 public void decodeIndexKey(char[] key) {
214     int last = key.length - 1;
215     this.parameterCount = 0;
216     this.declaringSimpleName = null;
217     int power = 1;
218     for (int i=last; i>=0; i--) {
219         if (key[i] == SEPARATOR) {
220             System.arraycopy(key, 0, this.declaringSimpleName = new char[i], 0, i);
221             break;
222         }
223         if (i == last) {
224             this.parameterCount = key[i] - '0';
225         } else {
226             power *= 10;
227             this.parameterCount += power * (key[i] - '0');
228         }
229     }
230 }
231 public SearchPattern getBlankPattern() {
232     return new ConstructorPattern(R_EXACT_MATCH | R_CASE_SENSITIVE);
233 }
234 public char[][] getIndexCategories() {
235     if (this.findReferences)
236         return this.findDeclarations ? REF_AND_DECL_CATEGORIES : REF_CATEGORIES;
237     if (this.findDeclarations)
238         return DECL_CATEGORIES;
239     return CharOperation.NO_CHAR_CHAR;
240 }
241 boolean hasConstructorArguments() {
242     return constructorArguments != null && constructorArguments.length > 0;
243 }
244 boolean hasConstructorParameters() {
245     return constructorParameters;
246 }
247 public boolean matchesDecodedKey(SearchPattern decodedPattern) {
248     ConstructorPattern pattern = (ConstructorPattern) decodedPattern;
249
250     return (this.parameterCount == pattern.parameterCount || this.parameterCount == -1 || this.varargs)
251         && matchesName(this.declaringSimpleName, pattern.declaringSimpleName);
252 }
253 protected boolean mustResolve() {
254     if (this.declaringQualification != null) return true;
255
256     // parameter types
257
if (this.parameterSimpleNames != null)
258         for (int i = 0, max = this.parameterSimpleNames.length; i < max; i++)
259             if (this.parameterQualifications[i] != null) return true;
260     return this.findReferences; // need to check resolved default constructors and explicit constructor calls
261
}
262 EntryResult[] queryIn(Index index) throws IOException JavaDoc {
263     char[] key = this.declaringSimpleName; // can be null
264
int matchRule = getMatchRule();
265
266     switch(getMatchMode()) {
267         case R_EXACT_MATCH :
268             if (this.isCamelCase) break;
269             if (this.declaringSimpleName != null && this.parameterCount >= 0 && !this.varargs)
270                 key = createIndexKey(this.declaringSimpleName, this.parameterCount);
271             else { // do a prefix query with the declaringSimpleName
272
matchRule &= ~R_EXACT_MATCH;
273                 matchRule |= R_PREFIX_MATCH;
274             }
275             break;
276         case R_PREFIX_MATCH :
277             // do a prefix query with the declaringSimpleName
278
break;
279         case R_PATTERN_MATCH :
280             if (this.parameterCount >= 0 && !this.varargs)
281                 key = createIndexKey(this.declaringSimpleName == null ? ONE_STAR : this.declaringSimpleName, this.parameterCount);
282             else if (this.declaringSimpleName != null && this.declaringSimpleName[this.declaringSimpleName.length - 1] != '*')
283                 key = CharOperation.concat(this.declaringSimpleName, ONE_STAR, SEPARATOR);
284             // else do a pattern query with just the declaringSimpleName
285
break;
286         case R_REGEXP_MATCH :
287             // TODO (frederic) implement regular expression match
288
break;
289     }
290
291     return index.query(getIndexCategories(), key, matchRule); // match rule is irrelevant when the key is null
292
}
293 protected StringBuffer JavaDoc print(StringBuffer JavaDoc output) {
294     if (this.findDeclarations) {
295         output.append(this.findReferences
296             ? "ConstructorCombinedPattern: " //$NON-NLS-1$
297
: "ConstructorDeclarationPattern: "); //$NON-NLS-1$
298
} else {
299         output.append("ConstructorReferencePattern: "); //$NON-NLS-1$
300
}
301     if (declaringQualification != null)
302         output.append(declaringQualification).append('.');
303     if (declaringSimpleName != null)
304         output.append(declaringSimpleName);
305     else if (declaringQualification != null)
306         output.append("*"); //$NON-NLS-1$
307

308     output.append('(');
309     if (parameterSimpleNames == null) {
310         output.append("..."); //$NON-NLS-1$
311
} else {
312         for (int i = 0, max = parameterSimpleNames.length; i < max; i++) {
313             if (i > 0) output.append(", "); //$NON-NLS-1$
314
if (parameterQualifications[i] != null) output.append(parameterQualifications[i]).append('.');
315             if (parameterSimpleNames[i] == null) output.append('*'); else output.append(parameterSimpleNames[i]);
316         }
317     }
318     output.append(')');
319     return super.print(output);
320 }
321 }
322
Popular Tags