• Java注解原理


    //获取注解对象
    public <T extends Annotation> T getAnnotation(Class<T> annotationClass) {
        return super.getAnnotation(annotationClass);
    }
    
     public <T extends Annotation> T getAnnotation(Class<T> annotationClass) {
            Objects.requireNonNull(annotationClass);
            return annotationClass.cast(declaredAnnotations().get(annotationClass));
        }
    
    private synchronized  Map<Class<? extends Annotation>, Annotation> declaredAnnotations() {
            if (declaredAnnotations == null) {
                Executable root = getRoot();
                if (root != null) {
                    declaredAnnotations = root.declaredAnnotations();
                } else {
                    declaredAnnotations = AnnotationParser.parseAnnotations(
                        getAnnotationBytes(),
                        sun.misc.SharedSecrets.getJavaLangAccess().
                        getConstantPool(getDeclaringClass()),
                        getDeclaringClass());
                }
            }
            return declaredAnnotations;
        }
    
    public static Map<Class<? extends Annotation>, Annotation> parseAnnotations(byte[] var0, ConstantPool var1, Class<?> var2) {
            if (var0 == null) {
                return Collections.emptyMap();
            } else {
                try {
                    return parseAnnotations2(var0, var1, var2, (Class[])null);
                } catch (BufferUnderflowException var4) {
                    throw new AnnotationFormatError("Unexpected end of annotations.");
                } catch (IllegalArgumentException var5) {
                    throw new AnnotationFormatError(var5);
                }
            }
        }
    
    private static Annotation parseAnnotation2(ByteBuffer var0, ConstantPool var1, Class<?> var2, boolean var3, Class<? extends Annotation>[] var4) {
            int var5 = var0.getShort() & 'uffff';
            Class var6 = null;
            String var7 = "[unknown]";
    
            try {
                try {
                    var7 = var1.getUTF8At(var5);
                    var6 = parseSig(var7, var2);
                } catch (IllegalArgumentException var18) {
                    var6 = var1.getClassAt(var5);
                }
            } catch (NoClassDefFoundError var19) {
                if (var3) {
                    throw new TypeNotPresentException(var7, var19);
                }
    
                skipAnnotation(var0, false);
                return null;
            } catch (TypeNotPresentException var20) {
                if (var3) {
                    throw var20;
                }
    
                skipAnnotation(var0, false);
                return null;
            }
    
            if (var4 != null && !contains(var4, var6)) {
                skipAnnotation(var0, false);
                return null;
            } else {
                AnnotationType var8 = null;
    
                try {
                    var8 = AnnotationType.getInstance(var6);
                } catch (IllegalArgumentException var17) {
                    skipAnnotation(var0, false);
                    return null;
                }
    
                Map var9 = var8.memberTypes();
                LinkedHashMap var10 = new LinkedHashMap(var8.memberDefaults());
                int var11 = var0.getShort() & 'uffff';
    
                for(int var12 = 0; var12 < var11; ++var12) {
                    int var13 = var0.getShort() & 'uffff';
                    String var14 = var1.getUTF8At(var13);
                    Class var15 = (Class)var9.get(var14);
                    if (var15 == null) {
                        skipMemberValue(var0);
                    } else {
                        Object var16 = parseMemberValue(var15, var0, var1, var2);
                        if (var16 instanceof AnnotationTypeMismatchExceptionProxy) {
                            ((AnnotationTypeMismatchExceptionProxy)var16).setMember((Method)var8.members().get(var14));
                        }
    
                        var10.put(var14, var16);//var14是注解属性名称,var16是对应的值
                    }
                }
    
                return annotationForMap(var6, var10);//这步生成代理类
            }
        }
    
     public static Annotation annotationForMap(final Class<? extends Annotation> var0, final Map<String, Object> var1) {
            return (Annotation)AccessController.doPrivileged(new PrivilegedAction<Annotation>() {
                public Annotation run() {
                    return (Annotation)Proxy.newProxyInstance(var0.getClassLoader(), new Class[]{var0}, new AnnotationInvocationHandler(var0, var1));//生成代理类
                }
            });
        }
    
    public static AnnotationType getInstance(Class<? extends Annotation> var0) {
            JavaLangAccess var1 = SharedSecrets.getJavaLangAccess();
            AnnotationType var2 = var1.getAnnotationType(var0);
            if (var2 == null) {
                var2 = new AnnotationType(var0);
                if (!var1.casAnnotationType(var0, (AnnotationType)null, var2)) {
                    var2 = var1.getAnnotationType(var0);
    
                    assert var2 != null;
                }
            }
    
            return var2;
        }
    
     String var7 = var6.getName();
                        Class var8 = var6.getReturnType();
                        this.memberTypes.put(var7, invocationHandlerReturnType(var8));
                        this.members.put(var7, var6);
                        Object var9 = var6.getDefaultValue();
                        if (var9 != null) {
                            this.memberDefaults.put(var7, var9);
                        }
                    }
                }
    
    //获取注解默认属性的
    public Object getDefaultValue() {
            if  (annotationDefault == null)
                return null;
            Class<?> memberType = AnnotationType.invocationHandlerReturnType(
                getReturnType());
            Object result = AnnotationParser.parseMemberValue(
                memberType, ByteBuffer.wrap(annotationDefault),
                sun.misc.SharedSecrets.getJavaLangAccess().
                    getConstantPool(getDeclaringClass()),
                getDeclaringClass());
            if (result instanceof sun.reflect.annotation.ExceptionProxy)
                throw new AnnotationFormatError("Invalid default: " + this);
            return result;
        }
    
    //获取注解非默认属性的
    Object var16 = parseMemberValue(var15, var0, var1, var2);
                        if (var16 instanceof AnnotationTypeMismatchExceptionProxy) {
                            ((AnnotationTypeMismatchExceptionProxy)var16).setMember((Method)var8.members().get(var14));
                        }
                        var10.put(var14, var16);
                    }
                }
    
    if (var1 != Retention.class && var1 != Inherited.class) {
                    JavaLangAccess var10 = SharedSecrets.getJavaLangAccess();
                    Map var11 = AnnotationParser.parseSelectAnnotations(var10.getRawClassAnnotations(var1), var10.getConstantPool(var1), var1, new Class[]{Retention.class, Inherited.class});//从这里开始获取非注解属性的
                    Retention var12 = (Retention)var11.get(Retention.class);
                    this.retention = var12 == null ? RetentionPolicy.CLASS : var12.value();
                    this.inherited = var11.containsKey(Inherited.class);
                }

    一个注解对应一个动态代理类,每个被注解标注的方法都对应一个map,每个被注解标注的方法都生成一个$Proxy0类实例

    总体步骤:先从常量池获取注解属性然后放进一个以方法名-属性值为键值对的map,然后JVM帮我们生成一个代理注解的$Proxy类,这个类代理了注解里的抽象方法,具体实现是从自己的map取出属性值然后返回

  • 相关阅读:
    函数
    文件处理及处理模式
    字符编码
    元组,字典和集合的用法
    数字类型、字符串和列表
    计算机硬件介绍
    数据类型及语法介绍
    初识python
    设计模式
    最近的时候
  • 原文地址:https://www.cnblogs.com/hanabivvv/p/14604299.html
Copyright © 2020-2023  润新知