JDK-4287725 : (reflect) Allow subclasses of stated argument types in Class.getMethod()
  • Type: Enhancement
  • Component: core-libs
  • Sub-Component: java.lang:reflect
  • Affected Version: 1.2.2,1.3.0
  • Priority: P4
  • Status: Open
  • Resolution: Unresolved
  • OS: generic,windows_98,windows_nt
  • CPU: generic,x86
  • Submitted: 1999-11-03
  • Updated: 2012-09-28
Related Reports
Duplicate :  
Duplicate :  
Relates :  
Relates :  
Description

Name: krT82822			Date: 11/03/99


java version "1.2.2"
Classic VM (build JDK-1.2.2-W, native threads, symcjit)

In its current form, the getMethod(String, Class[]) imposes a high degree
of precision in the Class argument it receives.  Specifically, if a
valid subclass of the 'proper' argument class is passed, a NoSuchMethodException
is thrown at compile-time.

The following demonstrates the principle:

import java.lang.reflect.*;

class Super { }

class Sub extends Super { }

public class Foo {

	public void bar(Super s) { System.out.println("Test"); }

	public static void main(String[] args) throws Throwable
		{
		 Sub sub = new Sub();
		 // This works as expected and advertised.
		 java.lang.reflect.Method method = Foo.class.getMethod("bar",
new Class[] { Super.class } );
		 
		 // The following throws a NoSuchMethodException, though sub is
an instance of a valid Super subclass
		 java.lang.reflect.Method method = Foo.class.getMethod("bar",
new Class[] { sub.getClass() } );
		 
		 // RFE: Allow for 'lazy' resolution to the most specific
applicable method,
		 // governed by the same rules that apply to the resolution of
multiple applicable
		 // methods at compile-time.
		 
		 method.invoke(new Foo(), new Object[] { sub });
		}
}

It would be of some utility if, when the Class passed into the getMethod method
is not of the precise type, its superclasses were queried and the most specific
valid method returned (following the same rules applied to overloaded methods
at compile time) if found.
(Review ID: 97431) 
======================================================================

Roger.Rawlinson@Ireland 2000-03-07

I've got a Licencee who is also asking for this functionality. 

I would also point out that the evaluation says that when a method is called
it's the job of the compiler to search for any sub classes that match. This is
true ONLY if a method has been declaired as final. For most cases I'd expect the
VM to have to perform the search. This means that the code to search for
subclasses in the parameter list is already in the VM, and consequently
implementing a new API should not effect the memory footprint too much.

I've attached a small test case which shows this.

-----
The same problem occurs with Class.getMethod, Class.getDeclaredMethod,
Class.getConstructor, and Class.getDeclaredConstructor.  Bug 4651775 contains a
request to specify the meaning of "match" in the javadoc for these methods.

-- iag@sfbay 2002-03-12

Comments
WORK AROUND Name: krT82822 Date: 11/03/99 Users of getMethod must be precise identifying the Class passed to the argument. ======================================================================
19-08-2004

SUGGESTED FIX Roger.Rawlinson@Ireland 2000-03-08 I suggest that we implement a new API which does allow the base classes to be considered when searching for a method. The narrowing of the parameters should work the same way for reflection as it currently does for a method call.
19-08-2004

EVALUATION The essence of this request is that the user would like for Class.getMethod to apply the same overloading rules as the compiler does. I think this is a reasonable request, as I see a need for this arising frequently in certain kinds of reflective programs, such as debuggers and scripting interpreters, and it would be helpful to have a standard implementation so that everybody gets it right. For compatibility, however, the behavior of the existing Class.getMethod should be left alone, and a new method defined. There is a case for leaving this functionality out on the basis of footprint, as it can be implemented using existing APIs, albeit somewhat inefficiently. william.maddox@Eng 1999-12-17 See also 4401287. neal.gafter@Eng 2001-08-02 Consensus appears to be that we should provide overload resolution in reflection. Exactly when such functionality is provided would depend largely on interest and potential uses. For compatibility reasons, the Class.get(Declared)+{Method,Constructor} implementation should not change; new method should be introduced. The specification for these methods does need to be modified to define "match". See bug 4651775. -- iag@sfbay 2002-03-12
12-03-2002