据说这不是一个新问题,但是我很难找到解决方案,因为对此的大多数答案都涉及到有问题的方法,而不是公开的。
有一个名为reflection
的程序包,其中定义了注释以及UITester
类,后者使用类注释和方法注释。名为gui
的其他程序包包含类MinimalUI
,该类随后测试对UITester
的访问,其方法以及相应的注释值。但是我遇到了NoSuchMethodException
。
功能注释
注释用于锁定/解锁方法。
package reflection;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import java.lang.annotation.ElementType;
@Retention( RetentionPolicy.RUNTIME )
@Target( {ElementType.METHOD} )
public @interface FunctionAnnotation
{
boolean locked();
}
样本注释
用于设置一些基本类属性的简单注释。
package reflection;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
@Retention( RetentionPolicy.RUNTIME )
public
@interface SampleAnnotation
{
String name();
String value();
boolean output();
}
UITester
这是带注释的类。类声明本身是带注释的,因此是该类的一种方法,因此使用了前面显示的两个注释。
package reflection;
@SampleAnnotation( name = "default", value = "[MINIMAL UI ANNOTATION] Testing.", output = true )
public class UITester
{
public UITester()
{
System.out.println( "[UI TESTER] Created." );
}
public void print( String value )
{
System.out.println( "[UI TESTER] Printing: " + value );
}
@FunctionAnnotation( locked = false )
public void printIfAvailable( String value )
{
System.out.println( "[UI TESTER] Printing (available): " + value );
}
}
MinimalUI
最后,在同一包中声明了一个最小的UI类,该类实现了Gui
接口。我只发布了相关的测试方法,因为否则此示例将变得有点大。以下代码是方法MinimalUI#testUI
。它需要读取为UITester
设置的注释,并根据结果进行操作。该实现是极简主义的,并且缺少保障措施,这很好,因为这是一个沙箱项目,我正在其中测试要转移到生产中的模式。代码:
@Override
public void testUI()
{
UITester tester = new UITester();
Annotation annotation = UITester.class.getAnnotation( SampleAnnotation.class );
if ( annotation instanceof SampleAnnotation )
{
String value = ( (SampleAnnotation) annotation ).value();
tester.print( value );
try
{
Method possiblyLockedMethod = UITester.class.getMethod( "printIfAvailable" );
Annotation methodLockCheck = possiblyLockedMethod.getAnnotation( FunctionAnnotation.class );
if ( !( ( FunctionAnnotation) methodLockCheck ).locked() ) tester.printIfAvailable( value );
}
catch( NoSuchMethodException e )
{
System.out.println( "[MINIMAL UI][ERROR] Cannot find method to be retrieved. Reflection failed. " + e.getMessage() );
}
catch( Exception e )
{
System.out.println( "[MINIMAL UI][ERROR] Exception during UI testing via reflection: " + e.getMessage() + " Exception: " + e.toString() );
}
}
else
{
System.out.println( "[MINIMAL UI][ERROR] Reflection error. Unable to read annotation!" );
}
}
运行MinimalUI#testUI
导致抛出NoSuchMethodException
,到目前为止,我仍然不明白为什么。引发异常的确切行是Method possiblyLockedMethod = UITester.class.getMethod( "printIfAvailable" );
。
getMethod
的行为吗?类声明可能会有所更改吗?printIfAvailable
被声明为public
,那么为什么找不到它?注释会以某种方式影响public
状态吗? @Retention( RetentionPolicy.RUNTIME )
注释,这是否有可能阻止在加载类或进行任何此类操作时定义函数?我认为这很简单,我很想念。目前没有我可以找到的错别字,那怎么了?
答案 0 :(得分:1)
调用UITester.class.getMethod( "printIfAvailable" )
意味着您正在尝试获取名为printIfAvailable
的方法,该方法需要 no 参数({{1}的parameterTypes
参数}是var-arg)。
但是,您的方法是使用getMethod
参数声明的。你应该用
String
答案 1 :(得分:1)
您现在的问题是您使用的getMethod
方法错误。您只搜索没有任何参数的方法。如果将其更改为此UITester.class.getMethod( "printIfAvailable", String.class );
,则可以正常使用。
JavaDoc:
/**
* Returns a {@code Method} object that reflects the specified public
* member method of the class or interface represented by this
* {@code Class} object. The {@code name} parameter is a
* {@code String} specifying the simple name of the desired method. The
* {@code parameterTypes} parameter is an array of {@code Class}
* objects that identify the method's formal parameter types, in declared
* order. If {@code parameterTypes} is {@code null}, it is
* treated as if it were an empty array.
* ...