4.7. Types, Reflection, and Dynamic Loading
The java.lang.Class class represents data
types in Java and, along with the classes in the
java.lang.reflect package, gives Java programs
the capability of introspection (or self-reflection); a
Java class can look at
itself, or any other class, and determine its superclass, what
methods it defines, and so on. There are several ways you can
obtain a Class object in Java:
// Obtain the Class of an arbitrary object o
Class c = o.getClass();
// Obtain a Class object for primitive types with various predefined constants
c = Void.TYPE; // The special "no-return-value" type
c = Byte.TYPE; // Class object that represents a byte
c = Integer.TYPE; // Class object that represents an int
c = Double.TYPE; // etc. See also Short, Character, Long, Float.
// Express a class literal as a type name followed by ".class"
c = int.class; // Same as Integer.TYPE
c = String.class; // Same as "dummystring".getClass()
c = byte[].class; // Type of byte arrays
c = Class[][].class; // Type of array of arrays of Class objects
Once you have a Class object, you can perform
some interesting reflective operations with it:
import java.lang.reflect.*;
Object o; // Some unknown object to investigate
Class c = o.getClass(); // Get its type
// If it is an array, figure out its base type
while (c.isArray()) c = c.getComponentType();
// If c is not a primitive type, print its class hierarchy
if (!c.isPrimitive()) {
for(Class s = c; s != null; s = s.getSuperclass())
System.out.println(s.getName() + " extends");
}
// Try to create a new instance of c; this requires a no-arg constructor
Object newobj = null;
try { newobj = c.newInstance(); }
catch (Exception e) {
// Handle InstantiationException, IllegalAccessException
}
// See if the class has a method named setText that takes a single String
// If so, call it with a string argument
try {
Method m = c.getMethod("setText", new Class[] { String.class });
m.invoke(newobj, new Object[] { "My Label" });
} catch(Exception e) { /* Handle exceptions here */ }
Class also provides a simple
mechanism for dynamic class loading in Java. For more complete
control over dynamic class loading, however, you should use a
java.lang.ClassLoader object, typically a
java.net.URLClassLoader. This technique
is useful, for example, when
you want to load a class that is named in a configuration
file instead of being hardcoded into your program:
// Dynamically load a class specified by name in a config file
String classname = // Look up the name of the class
config.getProperties("filterclass", // The property name
"com.davidflangan.filters.Default"); // A default
try {
Class c = Class.forName(classname); // Dynamically load the class
Object o = c.newInstance(); // Dynamically instantiate it
} catch (Exception e) { /* Handle exceptions */ }
// If the class to be loaded is not in the classpath, create a custom
// class loader to load it.
// Use the config file again to specify the custom path
import java.net.URLClassLoader;
String classdir = config.getProperties("classpath");
try {
ClassLoader loader = new URLClassLoader(new URL[] { new URL(classdir) });
Class c = loader.loadClass(classname);
}
catch (Exception e) { /* Handle exceptions */ }
 |  |  |
| 4.6. Collections |  | 4.8. Threads |

Copyright © 2001 O'Reilly & Associates. All rights reserved.
|
|