ホームページ >Java >&#&チュートリアル >Java の実行時にアノテーション パラメータ値を変更できますか?

Java の実行時にアノテーション パラメータ値を変更できますか?

Linda Hamilton
Linda Hamiltonオリジナル
2024-12-11 18:51:15361ブラウズ

Can Annotation Parameter Values Be Modified at Runtime in Java?

実行時にアノテーション パラメーター値を変更する

特定のパラメーター値で修飾されたアノテーションを持つクラスがあり、それを変更したいと考えているとします。実行時の値。すでに JVM にロードされているコンパイル済みクラスの注釈パラメータ値を変更することは可能ですか?

解決策:

はい、注釈パラメータを変更することは可能です実行時の値。次のアプローチを使用できます。

@SuppressWarnings("unchecked")
public static Object changeAnnotationValue(Annotation annotation, String key, Object newValue) {
    Object handler = Proxy.getInvocationHandler(annotation);
    Field f;
    try {
        f = handler.getClass().getDeclaredField("memberValues");
    } catch (NoSuchFieldException | SecurityException e) {
        throw new IllegalStateException(e);
    }
    f.setAccessible(true);
    Map<String, Object> memberValues;
    try {
        memberValues = (Map<String, Object>) f.get(handler);
    } catch (IllegalArgumentException | IllegalAccessException e) {
        throw new IllegalStateException(e);
    }
    Object oldValue = memberValues.get(key);
    if (oldValue == null || oldValue.getClass() != newValue.getClass()) {
        throw new IllegalArgumentException();
    }
    memberValues.put(key, newValue);
    return oldValue;
}

使用法:

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE)
public @interface ClassAnnotation {
  String value() default "";
}

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.FIELD)
public @interface FieldAnnotation {
  String value() default "";
}

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)
public @interface MethodAnnotation {
  String value() default "";
}

@ClassAnnotation("class test")
public static class TestClass {
    @FieldAnnotation("field test")
    public Object field;

    @MethodAnnotation("method test")
    public void method() {}
}

public static void main(String[] args) throws Exception {
    final ClassAnnotation classAnnotation = TestClass.class.getAnnotation(ClassAnnotation.class);
    System.out.println("old ClassAnnotation = " + classAnnotation.value());
    changeAnnotationValue(classAnnotation, "value", "another class annotation value");
    System.out.println("modified ClassAnnotation = " + classAnnotation.value());

    Field field = TestClass.class.getField("field");
    final FieldAnnotation fieldAnnotation = field.getAnnotation(FieldAnnotation.class);
    System.out.println("old FieldAnnotation = " + fieldAnnotation.value());
    changeAnnotationValue(fieldAnnotation, "value", "another field annotation value");
    System.out.println("modified FieldAnnotation = " + fieldAnnotation.value());

    Method method = TestClass.class.getMethod("method");
    final MethodAnnotation methodAnnotation = method.getAnnotation(MethodAnnotation.class);
    System.out.println("old MethodAnnotation = " + methodAnnotation.value());
    changeAnnotationValue(methodAnnotation, "value", "another method annotation value");
    System.out.println("modified MethodAnnotation = " + methodAnnotation.value());
}

このアプローチは、アノテーションの内部表現を直接変更することによって機能します。その結果、後続のリフレクション呼び出しでは、変更されたパラメーター値が取得されます。これには、新しいアノテーション インスタンスを作成する必要がないという利点があり、特定のアノテーション クラスについての事前の知識が不要になります。さらに、元のアノテーション インスタンスを変更しないことにより、副作用が最小限に抑えられます。

以上がJava の実行時にアノテーション パラメータ値を変更できますか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。