国产xxxx99真实实拍_久久不雅视频_高清韩国a级特黄毛片_嗯老师别我我受不了了小说

資訊專欄INFORMATION COLUMN

Java中的注解是怎樣工作的

edagarli / 530人閱讀

摘要:另一個很重要的因素是定義了一種標準的描述元數(shù)據(jù)的方式。對于注解,它的用戶就是虛擬機,工作在字節(jié)碼層面,在編譯階段進行檢查,其處理機制主要是內(nèi)部處理。

什么是注解

用一個詞就可以描述注解,那就是元數(shù)據(jù),即一種描述數(shù)據(jù)的數(shù)據(jù)。所以,可以說注解就是源代碼的元數(shù)據(jù)。比如,下面這段代碼:

@Override
public String toString() {
return "This is String Representation of current object.";
}

上面的代碼中,重寫了toString()方法并使用了@Override注解。

事實上,@Override告訴編譯器這個方法是一個重寫方法(描述方法的元數(shù)據(jù)),如果父類中不存在該方法,編譯器便會報錯,提示該方法沒有重寫父類中的方法。如果不小心拼寫錯誤,例如將toString()寫成了toStrring(){double r},而且也沒有使用@Override注解,那程序依然能編譯運行,但運行結(jié)果會和期望的大不相同。

Annotation是一種應(yīng)用于類、方法、參數(shù)、變量、構(gòu)造器及包聲明中的特殊修飾符。它是一種由JSR-175標準選擇用來描述元數(shù)據(jù)的一種工具。使用注解有助于閱讀程序。

為什么要引入注解

使用Annotation之前(甚至在使用之后),XML被廣泛的應(yīng)用于描述元數(shù)據(jù)。不知何時開始一些應(yīng)用開發(fā)人員和架構(gòu)師發(fā)現(xiàn)XML的維護越來越糟糕了。他們希望使用一些和代碼緊耦合的東西,而不是像XML那樣和代碼是松耦合的(在某些情況下甚至是完全分離的)代碼描述。如果你在Google中搜索“XML vs. annotations”,會看到許多關(guān)于這個問題的辯論。最有趣的是XML配置其實就是為了分離代碼和配置而引入的。上述兩種觀點可能會讓你很疑惑,兩者觀點似乎構(gòu)成了一種循環(huán),但各有利弊。下面我們通過一個例子來理解這兩者的區(qū)別。

假如你想為應(yīng)用設(shè)置很多的常量或參數(shù),這種情況下,XML是一個很好的選擇,因為它不會同特定的代碼相連。如果你想把某個方法聲明為服務(wù),那么使用Annotation會更好一些,因為這種情況下需要注解和方法緊密耦合起來,開發(fā)人員也必須認識到這點。

另一個很重要的因素是Annotation定義了一種標準的描述元數(shù)據(jù)的方式。在這之前,開發(fā)人員通常使用他們自己的方式定義元數(shù)據(jù)。例如,使用標記interfaces,注釋,transient關(guān)鍵字等等。每個程序員按照自己的方式定義元數(shù)據(jù),而不像Annotation這種標準的方式。

注解是如何工作的

當注解標注到某個類或者方法或者某個成員變量或者某個輸入?yún)?shù)上的時候,一定有一個對應(yīng)的機制來對注解標注的類、方法、成員變量和參數(shù)進行某些處理。

編寫Annotation非常簡單,注解本身也可以說是一個類。可以將Annotation的定義同接口的定義進行比較。看個例子,標準的注解@Override:

package java.lang;

import java.lang.annotation.*;

@Target(ElementType.METHOD)
@Retention(RetentionPolicy.SOURCE)
public @interface Override {
}

可以看見,@Override注解似乎什么都沒做,那它是如何檢查在父類中有一個同名的函數(shù)?@Override注解的定義僅僅是元數(shù)據(jù),不包含業(yè)務(wù)邏輯,而實現(xiàn)業(yè)務(wù)邏輯的就是注解的用戶。

對于@Override注解,它的用戶就是JVM虛擬機,工作在字節(jié)碼層面,在編譯階段進行檢查,其處理機制主要是JVM內(nèi)部處理。

再例如Spring中的 @Service 注解,Spring在啟動IOC容器的時候會對每個類進行掃描,把所有標注@Component及其子注解如@Service的類進行Bean處理。

編寫自定義的注解

JDK5.0版本在 java.lang.annotation提供了四種元注解,專門注解其他的注解:

@Documented – 是否將注解信息添加在java文檔中

@Retention – 定義該注解的生命周期

@Target –注解用于什么地方

@Inherited – 是否允許子類繼承該注解

@Retention 注解定義該注解的生命周期,在什么階段丟棄,

RetentionPolicy.SOURCE – 在編譯階段丟棄。這些注解在編譯結(jié)束之后就不再有任何意義,所以它們不會寫入字節(jié)碼。@Override, @SuppressWarnings都屬于這類注解。

RetentionPolicy.CLASS – 在類加載的時候丟棄,在字節(jié)碼文件的處理中有用。注解默認使用這種方式。

RetentionPolicy.RUNTIME – 始終不會丟棄,運行期也保留該注解,因此可以使用反射機制讀取該注解的信息。自定義的注解通常使用這種方式。

@Target – 表示該注解用于什么地方。如果不明確指出,該注解可以放在任何地方。屬性的注解是兼容的。

ElementType.TYPE:用于描述類、接口或enum聲明

ElementType.FIELD:用于描述實例變量

ElementType.METHOD

ElementType.PARAMETER

ElementType.CONSTRUCTOR

ElementType.LOCAL_VARIABLE

ElementType.ANNOTATION_TYPE 另一個注釋

ElementType.PACKAGE 用于記錄java文件的package信息

那么,注解的內(nèi)部到底是如何定義的呢?Annotations只支持基本類型、String及枚舉類型。注釋中所有的屬性被定義成方法,并允許提供默認值。

定義一個 @AuthCheck 注解,作用在SpringMVC controller的方法上。

package com.liuning.sys.auth;

import static java.lang.annotation.ElementType.METHOD;

import java.lang.annotation.Documented;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

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

注解中只有一個屬性,可以直接命名為“value”,使用時無需再標明屬性名。

在Spring的攔截器HandlerInterceptor中實現(xiàn)@AuthCheck注解的業(yè)務(wù)邏輯,這里使用了反射機制。

@Override
public boolean preHandle(HttpServletRequest request, 
                         HttpServletResponse response, 
                         Object handler) throws Exception {
    HandlerMethod hm = (HandlerMethod) handler;
    AuthCheck ac = hm.getMethodAnnotation(AuthCheck.class);
    if (ac != null) {
        if (ac.value() == "Login") {
            //進行業(yè)務(wù)邏輯操作
        }
    }
    return true;
}

下面的例子演示了如何使用上面的注解。使用了該注解的方法在用戶調(diào)用的時候會需要用戶已登錄。

@PostMapping("/list")
@AuthCheck(value = "Login")
public List getUserList(@RequestBody @Valid User user) {
    
    return userService.getUserList(user);
}

文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請注明本文地址:http://specialneedsforspecialkids.com/yun/75128.html

相關(guān)文章

  • 一個兩年Java面試總結(jié)

    摘要:數(shù)據(jù)結(jié)構(gòu)和算法樹快速排序,堆排序,插入排序其實八大排序算法都應(yīng)該了解一致性算法,一致性算法的應(yīng)用的內(nèi)存結(jié)構(gòu)。如何存儲一個的。八大排序算法一定要手敲一遍快排,堆排尤其重要。面試是一個雙向選擇的過程,不要抱著畏懼的心態(tài)去面試,不利于自己的發(fā)揮。 前言 16年畢業(yè)到現(xiàn)在也近兩年了,最近面試了阿里集團(菜鳥網(wǎng)絡(luò),螞蟻金服),網(wǎng)易,滴滴,點我達,最終收到點我達,網(wǎng)易offer,螞蟻金服二面掛掉,...

    anRui 評論0 收藏0
  • 2017 Android 面試題 [ 基礎(chǔ)與細節(jié) ]

    摘要:操作完成后,服務(wù)會自行停止運行。創(chuàng)建工作隊列,用于將逐一傳遞給實現(xiàn),這樣您就永遠不必擔心多線程問題。是的消息機制,集中解決線程間通信問題。 2017 Android 面試題 [ 基礎(chǔ)與細節(jié) ] 感謝@chuyao拋出的這些問題,平時業(yè)務(wù)代碼寫多了,很多基礎(chǔ)的東西變得含糊不清了,這次裸辭出來找工作確實沒有之前順利,順便求上海Android開發(fā)的坑。我自己整理了些答案,不對或者不妥的地方請...

    sydMobile 評論0 收藏0

發(fā)表評論

0條評論

最新活動
閱讀需要支付1元查看
<