Java tutorial
//package com.java2s; import java.lang.reflect.Constructor; import java.lang.reflect.Field; public class Main { /** * Sets the given field's value of the specified object instance. * * @throws IllegalArgumentException if the value cannot be set. */ public static void setValue(final Field field, final Object instance, final Object value) { try { field.setAccessible(true); field.set(instance, convert(value, field.getType())); } catch (final IllegalAccessException e) { throw new IllegalArgumentException("No access to field: " + field.getName(), e); } } /** * Converts the given object to an object of the specified type. The object is * casted directly if possible, or else a new object is created using the * destination type's public constructor that takes the original object as * input (except when converting to {@link String}, which uses the * {@link Object#toString()} method instead). In the case of primitive types, * returns an object of the corresponding wrapped type. If the destination * type does not have an appropriate constructor, returns null. * * @param <T> Type to which the object should be converted. * @param value The object to convert. * @param type Type to which the object should be converted. */ public static <T> T convert(final Object value, final Class<T> type) { if (value == null) return getNullValue(type); // ensure type is well-behaved, rather than a primitive type final Class<T> saneType = getNonprimitiveType(type); // cast the existing object, if possible if (canCast(value, saneType)) return cast(value, saneType); // special cases for strings if (value instanceof String) { // source type is String final String s = (String) value; if (s.isEmpty()) { // return null for empty strings return getNullValue(type); } // use first character when converting to Character if (saneType == Character.class) { final Character c = new Character(s.charAt(0)); @SuppressWarnings("unchecked") final T result = (T) c; return result; } } if (saneType == String.class) { // destination type is String; use Object.toString() method final String sValue = value.toString(); @SuppressWarnings("unchecked") final T result = (T) sValue; return result; } // wrap the original object with one of the new type, using a constructor try { final Constructor<T> ctor = saneType.getConstructor(value.getClass()); return ctor.newInstance(value); } catch (final Exception exc) { // no known way to convert return null; } } /** * Gets the "null" value for the given type. For non-primitives, this will * actually be null. For primitives, it will be zero for numeric types, false * for boolean, and the null character for char. */ public static <T> T getNullValue(final Class<T> type) { final Object defaultValue; if (type == boolean.class) defaultValue = false; else if (type == byte.class) defaultValue = (byte) 0; else if (type == char.class) defaultValue = '\0'; else if (type == double.class) defaultValue = 0d; else if (type == float.class) defaultValue = 0f; else if (type == int.class) defaultValue = 0; else if (type == long.class) defaultValue = 0L; else if (type == short.class) defaultValue = (short) 0; else defaultValue = null; @SuppressWarnings("unchecked") final T result = (T) defaultValue; return result; } /** * Returns the non-primitive {@link Class} closest to the given type. * <p> * Specifically, the following type conversions are done: * <ul> * <li>boolean.class becomes Boolean.class</li> * <li>byte.class becomes Byte.class</li> * <li>char.class becomes Character.class</li> * <li>double.class becomes Double.class</li> * <li>float.class becomes Float.class</li> * <li>int.class becomes Integer.class</li> * <li>long.class becomes Long.class</li> * <li>short.class becomes Short.class</li> * <li>void.class becomes Void.class</li> * </ul> * All other types are unchanged. * </p> */ public static <T> Class<T> getNonprimitiveType(final Class<T> type) { final Class<?> destType; if (type == boolean.class) destType = Boolean.class; else if (type == byte.class) destType = Byte.class; else if (type == char.class) destType = Character.class; else if (type == double.class) destType = Double.class; else if (type == float.class) destType = Float.class; else if (type == int.class) destType = Integer.class; else if (type == long.class) destType = Long.class; else if (type == short.class) destType = Short.class; else if (type == void.class) destType = Void.class; else destType = type; @SuppressWarnings("unchecked") final Class<T> result = (Class<T>) destType; return result; } /** * Checks whether objects of the given class can be cast to the specified * type. * * @see #cast(Object, Class) */ public static boolean canCast(final Class<?> c, final Class<?> type) { return type.isAssignableFrom(c); } /** * Checks whether the given object can be cast to the specified type. * * @see #cast(Object, Class) */ public static boolean canCast(final Object obj, final Class<?> type) { return canCast(obj.getClass(), type); } /** * Casts the given object to the specified type, or null if the types are * incompatible. */ public static <T> T cast(final Object obj, final Class<T> type) { if (!canCast(obj, type)) return null; @SuppressWarnings("unchecked") final T result = (T) obj; return result; } }