Java 注解(Annotations) 詳解


注解是元數據

注解是一種裝飾器、一個標記(maker),應用於Java的各種結構之上,例如類、方法、字段。用來為這些結構綁定元數據。注解不包含任何業務邏輯
只由運行時框架或編譯器根據注解信息去執行具體行為。

Retention and Target

保留(Retention )策略指定就程序生命周期而言,注釋應該保留多長時間(一個)
目標(Target)指定注解可以應用於哪些Java結構 (多個)

自定義annotation

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.FIELD)
public @interface JsonField {
    public String value() default "";
}
public class Car {
    @JsonField("manufacturer")
    private final String make;
    @JsonField
    private final String model;
    private final String year;

    public Car(String make, String model, String year) {
        this.make = make;
        this.model = model;
        this.year = year;
    }

    ## get and set method

    @Override
    public String toString() {
        return year + " " + make + " " + model;
    }
}

利用反射機制執行具體行為

public class JsonSerializer {

    public String serialize(Object object) throws JsonSerializeException {
        try {
            Class<?> objectClass = requireNonNull(object).getClass();
            Map<String, String> jsonElements = new HashMap<>();

            for (Field field: objectClass.getDeclaredFields()) {
                field.setAccessible(true);
                if (field.isAnnotationPresent(JsonField.class)) {
                    jsonElements.put(getSerializedKey(field), (String)field.get(object));
                }
            }

            System.out.println(toJsonString(jsonElements));
            return toJsonString(jsonElements);

        } catch (IllegalAccessException e) {
            throw new JsonSerializeException(e.getMessage());
        }
    }

    private String toJsonString(Map<String, String> jsonMap) {
        String elementsString = jsonMap.entrySet()
                .stream()
                .map(entry -> "\""  + entry.getKey() + "\":\"" + entry.getValue() + "\"")
                .collect(Collectors.joining(","));
        return "{" + elementsString + "}";
    }

    private String getSerializedKey(Field field) {
        String annotationValue = field.getAnnotation(JsonField.class).value();

        if (annotationValue.isEmpty()) {
            return  field.getName();
        } else {
            return annotationValue;
        }
    }
}
Car car = new Car("Ford", "F150", "2018");
JsonSerializer serializer = new JsonSerializer();
serializer.serialize(car);

# output
# {"model":"F150","manufacturer":"Ford"}

總結

雖然注解不應該用來代替接口或其他以面向對象的方式正確完成任務的語言結構,但它們可以極大地簡化重復的邏輯。
利用注解,可以以聲明式的編程方式,將與具體業務領域無關的功能(安全、事務、日志)等抽離出來。實現不同邏輯的解耦。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM