aboutsummaryrefslogtreecommitdiff
path: root/src/com/google/caliper/Parameter.java
diff options
context:
space:
mode:
authorJesse Wilson <jessewilson@google.com>2010-01-13 17:12:18 -0800
committerJesse Wilson <jessewilson@google.com>2010-01-13 17:12:18 -0800
commitf062bf49c71013ec19cb71218778299535aceaa8 (patch)
tree17acfe2a694f55828f64caaae4c25179e61525a8 /src/com/google/caliper/Parameter.java
parent1440b36663f61ebde1952d91b4a1f4c1a27fcefa (diff)
downloadcaliper-f062bf49c71013ec19cb71218778299535aceaa8.tar.gz
Update Caliper to r71.
Diffstat (limited to 'src/com/google/caliper/Parameter.java')
-rw-r--r--src/com/google/caliper/Parameter.java95
1 files changed, 71 insertions, 24 deletions
diff --git a/src/com/google/caliper/Parameter.java b/src/com/google/caliper/Parameter.java
index 1ba77b5..caca252 100644
--- a/src/com/google/caliper/Parameter.java
+++ b/src/com/google/caliper/Parameter.java
@@ -16,8 +16,19 @@
package com.google.caliper;
-import java.lang.reflect.*;
-import java.util.*;
+import java.lang.reflect.Field;
+import java.lang.reflect.Member;
+import java.lang.reflect.Method;
+import java.lang.reflect.Modifier;
+import java.lang.reflect.ParameterizedType;
+import java.lang.reflect.Type;
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.EnumSet;
+import java.util.Map;
+import java.util.Set;
+import java.util.TreeMap;
/**
* A parameter in a {@link SimpleBenchmark}.
@@ -35,22 +46,35 @@ abstract class Parameter<T> {
*/
public static Map<String, Parameter<?>> forClass(Class<? extends Benchmark> suiteClass) {
Map<String, Parameter<?>> parameters = new TreeMap<String, Parameter<?>>();
- for (final Field field : suiteClass.getDeclaredFields()) {
+ for (Field field : suiteClass.getDeclaredFields()) {
if (field.isAnnotationPresent(Param.class)) {
field.setAccessible(true);
- Parameter parameter = Parameter.forField(suiteClass, field);
+ Parameter<?> parameter = forField(suiteClass, field);
parameters.put(parameter.getName(), parameter);
}
}
return parameters;
}
- public static Parameter forField(
+ private static Parameter<?> forField(
Class<? extends Benchmark> suiteClass, final Field field) {
- Parameter result = null;
+ // First check for String values on the annotation itself
+ final Object[] defaults = field.getAnnotation(Param.class).value();
+ if (defaults.length > 0) {
+ return new Parameter<Object>(field) {
+ @Override public Collection<Object> values() throws Exception {
+ return Arrays.asList(defaults);
+ }
+ };
+ // TODO: or should we continue so we can give an error/warning if params are also give in a
+ // method or field?
+ }
+
+ Parameter<?> result = null;
Type returnType = null;
Member member = null;
+ // Now check for a fooValues() method
try {
final Method valuesMethod = suiteClass.getDeclaredMethod(field.getName() + "Values");
valuesMethod.setAccessible(true);
@@ -58,13 +82,14 @@ abstract class Parameter<T> {
returnType = valuesMethod.getGenericReturnType();
result = new Parameter<Object>(field) {
@SuppressWarnings("unchecked") // guarded below
- public Collection<Object> values() throws Exception {
+ @Override public Collection<Object> values() throws Exception {
return (Collection<Object>) valuesMethod.invoke(null);
}
};
} catch (NoSuchMethodException ignored) {
}
+ // Now check for a fooValues field
try {
final Field valuesField = suiteClass.getDeclaredField(field.getName() + "Values");
valuesField.setAccessible(true);
@@ -75,36 +100,58 @@ abstract class Parameter<T> {
returnType = valuesField.getGenericType();
result = new Parameter<Object>(field) {
@SuppressWarnings("unchecked") // guarded below
- public Collection<Object> values() throws Exception {
+ @Override public Collection<Object> values() throws Exception {
return (Collection<Object>) valuesField.get(null);
}
};
} catch (NoSuchFieldException ignored) {
}
- if (result == null) {
- throw new ConfigurationException("No values member defined for " + field);
+ if (member != null && !Modifier.isStatic(member.getModifiers())) {
+ throw new ConfigurationException("Values member must be static " + member);
+ }
+
+ // If there isn't a values member but the parameter is an enum, we default
+ // to EnumSet.allOf.
+ if (member == null && field.getType().isEnum()) {
+ returnType = Collection.class;
+ result = new Parameter<Object>(field) {
+ // TODO: figure out the simplest way to make this compile and be green in IDEA too
+ @SuppressWarnings({"unchecked", "RawUseOfParameterizedType", "RedundantCast"})
+ // guarded above
+ @Override public Collection<Object> values() throws Exception {
+ Set<Enum> set = EnumSet.allOf((Class<Enum>) field.getType());
+ return (Collection) set;
+ }
+ };
}
- if (!Modifier.isStatic(member.getModifiers())) {
- throw new ConfigurationException("Values member must be static " + member);
+ if (result == null) {
+ return new Parameter<Object>(field) {
+ @Override public Collection<Object> values() {
+ // TODO: need tests to make sure this fails properly when no cmdline params given and
+ // works properly when they are given
+ return Collections.emptySet();
+ }
+ };
+ } else if (!isValidReturnType(returnType)) {
+ throw new ConfigurationException("Invalid return type " + returnType
+ + " for values member " + member + "; must be Collection");
}
+ return result;
+ }
- // validate return type
- boolean valid = false;
+ private static boolean isValidReturnType(Type returnType) {
+ if (returnType == Collection.class) {
+ return true;
+ }
if (returnType instanceof ParameterizedType) {
ParameterizedType type = (ParameterizedType) returnType;
if (type.getRawType() == Collection.class) {
- valid = true;
+ return true;
}
}
-
- if (!valid) {
- throw new ConfigurationException("Invalid return type " + returnType
- + " for values member " + member + "; must be Collection");
- }
-
- return result;
+ return false;
}
/**
@@ -129,7 +176,7 @@ abstract class Parameter<T> {
/**
* Returns the field's name.
*/
- public String getName() {
+ String getName() {
return field.getName();
}
-} \ No newline at end of file
+}