setArity(Arity.OPTIONAL);
Ruby runtime = host.getRuntime();
// initialize all the callables for this method
JavaCallable callable = null;
JavaCallable[][] callables = null;
JavaCallable[] varargsCallables = null;
int varargsArity = Integer.MAX_VALUE;
if (members.length == 1) {
callable = createCallable(runtime, members[0]);
if (callable.isVarArgs()) {
varargsCallables = createCallableArray(callable);
}
} else {
Map<Integer, List<JavaCallable>> methodsMap = new HashMap<Integer, List<JavaCallable>>();
List<JavaCallable> varargsMethods = new ArrayList();
int maxArity = 0;
for (Member method: members) {
int currentArity = getMemberParameterTypes(method).length;
maxArity = Math.max(currentArity, maxArity);
List<JavaCallable> methodsForArity = methodsMap.get(currentArity);
if (methodsForArity == null) {
methodsForArity = new ArrayList<JavaCallable>();
methodsMap.put(currentArity,methodsForArity);
}
JavaCallable javaMethod = createCallable(runtime,method);
methodsForArity.add(javaMethod);
if (isMemberVarArgs(method)) {
varargsArity = Math.min(currentArity - 1, varargsArity);
varargsMethods.add(javaMethod);
}
}
callables = createCallableArrayArray(maxArity + 1);
for (Map.Entry<Integer,List<JavaCallable>> entry : methodsMap.entrySet()) {
List<JavaCallable> methodsForArity = (List<JavaCallable>)entry.getValue();
JavaCallable[] methodsArray = methodsForArity.toArray(createCallableArray(methodsForArity.size()));
callables[((Integer)entry.getKey()).intValue()] = methodsArray;
}
if (varargsMethods.size() > 0) {
// have at least one varargs, build that map too
varargsCallables = createCallableArray(varargsMethods.size());
varargsMethods.toArray(varargsCallables);
}
}
members = null;
// initialize cache of parameter types to method
// FIXME: No real reason to use CHM, is there?
cache = new ConcurrentHashMap(0, 0.75f, 1);
this.javaCallable = callable;
this.javaCallables = callables;
this.javaVarargsCallables = varargsCallables;
this.minVarargsArity = varargsArity;
// if it's not overloaded, set up a NativeCall
if (javaCallable != null) {
// no constructor support yet
if (javaCallable instanceof org.jruby.javasupport.JavaMethod) {
org.jruby.javasupport.JavaMethod javaMethod = (org.jruby.javasupport.JavaMethod)javaCallable;
Method method = (Method)javaMethod.getValue();
// only public, since non-public don't bind
if (Modifier.isPublic(method.getModifiers()) && Modifier.isPublic(method.getDeclaringClass().getModifiers())) {
setNativeCall(method.getDeclaringClass(), method.getName(), method.getReturnType(), method.getParameterTypes(), Modifier.isStatic(method.getModifiers()), true);
}
}