自定義注解

注解分類(lèi)

1、代碼注解
2围辙、編譯時(shí)注解
3我碟、運(yùn)行時(shí)注解

  • 注解范例
package com.alan.oa.biz.test;


import java.lang.annotation.*;

/**
 * 通過(guò)@interface關(guān)鍵字定義注解
 */
//源注解,@Target 說(shuō)明此注解可以作用的相關(guān)區(qū)域姚建,例如方法上類(lèi)矫俺,接口上。
@Target({ElementType.METHOD,ElementType.FIELD})
/*
 * @Retention生命周期
 * 1掸冤、RetentionPolicy.SOURCE 只在源碼顯示厘托,編譯時(shí)會(huì)丟棄
 * 2、RetentionPolicy.CLASS  編譯時(shí)會(huì)記錄到class中稿湿,運(yùn)行時(shí)忽略
 * 3铅匹、RetentionPolicy.RUNTIME 運(yùn)行時(shí)存在,可以通過(guò)反射讀取
 */
@Retention(RetentionPolicy.RUNTIME)
// 允許子類(lèi)只注解來(lái)繼承
@Inherited
// javadoc *.java 時(shí)會(huì)包含注解
@Documented
public @interface AnnotationDemo1 {

    // 成員的類(lèi)型是受限的饺藤,合法的類(lèi)型包括原始類(lèi)型及String,Class,Annotation,Enumeration
    // 如果注解只有一個(gè)成員包斑,則成員名必須取名為value(),在使用時(shí)可以忽略成員名和賦值號(hào)(=)
    // 注解類(lèi)可以沒(méi)用成員,沒(méi)有成員的注解成為標(biāo)識(shí)注解
    // 成員以無(wú)參無(wú)異常方式聲明
    String desc();
    String author();
    // 可以用default為成員指定一個(gè)默認(rèn)值
    int age() default 18;
}
  • 使用注解的類(lèi)
package com.alan.oa.biz.test;


@AnnotationDemo1("我是類(lèi)注解")
public class Demo1 {

    // 使用剛才定義的注解
    @AnnotationDemo1("我是方法注解")
    public String eyeColor(){
        return "red";
    }

    // 使用剛才定義的注解
    @AnnotationDemo1("我是方法注解222")
    public String eyeColor1(){
        return "red";
    }
}
  • 注解解析類(lèi)
package com.alan.oa.biz.test;

import java.lang.annotation.Annotation;
import java.lang.reflect.Method;

/**
 * 對(duì)注解進(jìn)行解析的類(lèi)
 */
public class ParseAnn {

    public static void main(String[] args) {
        // 1涕俗、使用類(lèi)加載器加載類(lèi)
        try {
            Class  c  = Class.forName("com.alan.oa.biz.test.Demo1");
            // 2罗丰、找到類(lèi)上面的注解 判斷當(dāng)前類(lèi)是否存在AnnotationDemo1注解
            boolean annotationPresent = c.isAnnotationPresent(AnnotationDemo1.class);
            if(annotationPresent){
                //3、拿到注解實(shí)例
                AnnotationDemo1 annotation = (AnnotationDemo1) c.getAnnotation(AnnotationDemo1.class);
                System.out.println(annotation.value());
            }
            // 4咽袜、找到方法上的注解,注意這里是方法數(shù)組
            Method[] method = c.getMethods();
            for(Method m:method){
                boolean annotationPresent1 =m.isAnnotationPresent(AnnotationDemo1.class);
                if(annotationPresent1){
                    AnnotationDemo1 annotation = m.getAnnotation(AnnotationDemo1.class);
                    System.out.println(annotation.value());
                }
            }
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        }

    }

注解實(shí)戰(zhàn)

  • 需求
    1丸卷、有一張用戶表,字段包括用戶id,用戶名询刹,昵稱(chēng)谜嫉,年齡萎坷,性別,所在城市沐兰,郵箱哆档,手機(jī)號(hào)。
    2住闯、方便的對(duì)每個(gè)字段或字段的組合條件進(jìn)行檢索瓜浸,并打印出sql。
    3比原、使用方式足夠簡(jiǎn)單插佛。

  • 實(shí)體類(lèi)

package com.alan.oa.biz.test;

/**
 * 通過(guò)自定義注解映射數(shù)據(jù)庫(kù)表和字段
 */

@Table("user")
public class Fliter {

    @Column("id")
    private  int id;

    @Column("user_name")
    private String userName;

    @Column("nick_name")
    private String nickName;

    @Column("age")
    private int age;

    @Column("city")
    private String city;

    @Column("email")
    private String email;

    @Column("mobile")
    private String mobile;

    //getter和setter方法

    public int getId() {
        return id;
    }

    public void setId(int id) {
        this.id = id;
    }

    public String getUserName() {
        return userName;
    }

    public void setUserName(String userName) {
        this.userName = userName;
    }

    public String getNickName() {
        return nickName;
    }

    public void setNickName(String nickName) {
        this.nickName = nickName;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    public String getCity() {
        return city;
    }

    public void setCity(String city) {
        this.city = city;
    }

    public String getEmail() {
        return email;
    }

    public void setEmail(String email) {
        this.email = email;
    }

    public String getMobile() {
        return mobile;
    }

    public void setMobile(String mobile) {
        this.mobile = mobile;
    }
}
  • 注解類(lèi)
package com.alan.oa.biz.test;


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

@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
public @interface Table {

    String value();
}
package com.alan.oa.biz.test;


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

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


  • 注解解析類(lèi)
package com.alan.oa.biz.test;

import java.lang.annotation.Annotation;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;

public class FilterTest {


    public static void main(String[] args) {

        // 查詢id為10的用戶
        Fliter f1 = new Fliter();
        f1.setId(10);

        // 查詢姓名為lucy的用戶
        Fliter f2 = new Fliter();
        f2.setUserName("lucy");

        //查詢郵箱為其中任意一個(gè)的用戶
        Fliter f3 = new Fliter();
        f3.setEmail("liu@sina.com,zh@163.com,77777@qq.com");

        String sql1 = query(f1);
        String sql2 = query(f2);
        String sql3 = query(f3);

        System.out.println(sql1);
        System.out.println(sql2);
        System.out.println(sql3);
    }

    private static String query(Fliter f){

        StringBuilder sb = new StringBuilder();
        // 1、獲取到class
        Class c = f.getClass();
        // 2量窘、獲取到table的名字
        boolean annotationPresent = c.isAnnotationPresent(Table.class);
        if(annotationPresent)
        {
            Table t = (Table) c.getAnnotation(Table.class );
            String tableName = t.value();
            sb.append("select * from ").append(tableName).append(" where 1=1");

        }
        // 3雇寇、遍歷所有的字段
        Field[] fields = c.getDeclaredFields();
        for(Field field:fields){
            // 4、處理每個(gè)字段對(duì)應(yīng)的sql
            // 4.1蚌铜、拿到字段名
            boolean annotationPresent1 = field.isAnnotationPresent(Column.class);
            String columnValue = null;
            if(annotationPresent1){
                Column column = field.getAnnotation(Column.class);
                columnValue = column.value();
            }
            //4.2锨侯、拿到字段的值
            String filedName = field.getName();
            String getMethodName = "get" + filedName.substring(0,1).toUpperCase() + filedName.substring(1);
            Object fieldValue = null;
            try {
                Method getMethod = c.getMethod(getMethodName);
                //拿到了字段的值
                fieldValue =  getMethod.invoke(f);
            } catch (NoSuchMethodException e) {
                e.printStackTrace();
            } catch (IllegalAccessException e) {
                e.printStackTrace();
            } catch (InvocationTargetException e) {
                e.printStackTrace();
            }

            //4.3、拼裝sql
            if(fieldValue == null || (fieldValue instanceof Integer && (Integer)fieldValue == 0)) {
                continue;
            }
            sb.append(" and ").append(columnValue);
            if(fieldValue instanceof String){
                if(((String) fieldValue).contains(",")){
                    String[] values = ((String) fieldValue).split(",");
                    sb.append(" in(");
                    for(String str:values){
                        sb.append("'").append(str).append("'").append(",");
                    }
                        sb.deleteCharAt(sb.length()-1);
                        sb.append(")");
                }else {
                    sb.append("=").append("'").append(fieldValue).append("'");
                }
            }else {
                sb.append("=").append(fieldValue);
            }

        }
        return sb.toString();
    }
}
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末冬殃,一起剝皮案震驚了整個(gè)濱河市囚痴,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌审葬,老刑警劉巖深滚,帶你破解...
    沈念sama閱讀 210,978評(píng)論 6 490
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異涣觉,居然都是意外死亡成箫,警方通過(guò)查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 89,954評(píng)論 2 384
  • 文/潘曉璐 我一進(jìn)店門(mén)旨枯,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái),“玉大人混驰,你說(shuō)我怎么就攤上這事攀隔。” “怎么了栖榨?”我有些...
    開(kāi)封第一講書(shū)人閱讀 156,623評(píng)論 0 345
  • 文/不壞的土叔 我叫張陵昆汹,是天一觀的道長(zhǎng)。 經(jīng)常有香客問(wèn)我婴栽,道長(zhǎng)满粗,這世上最難降的妖魔是什么? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 56,324評(píng)論 1 282
  • 正文 為了忘掉前任愚争,我火速辦了婚禮映皆,結(jié)果婚禮上挤聘,老公的妹妹穿的比我還像新娘。我一直安慰自己捅彻,他們只是感情好组去,可當(dāng)我...
    茶點(diǎn)故事閱讀 65,390評(píng)論 5 384
  • 文/花漫 我一把揭開(kāi)白布。 她就那樣靜靜地躺著步淹,像睡著了一般从隆。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上缭裆,一...
    開(kāi)封第一講書(shū)人閱讀 49,741評(píng)論 1 289
  • 那天键闺,我揣著相機(jī)與錄音,去河邊找鬼澈驼。 笑死辛燥,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的盅藻。 我是一名探鬼主播购桑,決...
    沈念sama閱讀 38,892評(píng)論 3 405
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼氏淑!你這毒婦竟也來(lái)了勃蜘?” 一聲冷哼從身側(cè)響起,我...
    開(kāi)封第一講書(shū)人閱讀 37,655評(píng)論 0 266
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤假残,失蹤者是張志新(化名)和其女友劉穎缭贡,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體辉懒,經(jīng)...
    沈念sama閱讀 44,104評(píng)論 1 303
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡阳惹,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,451評(píng)論 2 325
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了眶俩。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片莹汤。...
    茶點(diǎn)故事閱讀 38,569評(píng)論 1 340
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖颠印,靈堂內(nèi)的尸體忽然破棺而出纲岭,到底是詐尸還是另有隱情,我是刑警寧澤线罕,帶...
    沈念sama閱讀 34,254評(píng)論 4 328
  • 正文 年R本政府宣布止潮,位于F島的核電站,受9級(jí)特大地震影響钞楼,放射性物質(zhì)發(fā)生泄漏喇闸。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,834評(píng)論 3 312
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望燃乍。 院中可真熱鬧唆樊,春花似錦、人聲如沸橘沥。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 30,725評(píng)論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)座咆。三九已至痢艺,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間介陶,已是汗流浹背堤舒。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 31,950評(píng)論 1 264
  • 我被黑心中介騙來(lái)泰國(guó)打工, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留哺呜,地道東北人舌缤。 一個(gè)月前我還...
    沈念sama閱讀 46,260評(píng)論 2 360
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像某残,于是被迫代替她去往敵國(guó)和親国撵。 傳聞我的和親對(duì)象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 43,446評(píng)論 2 348

推薦閱讀更多精彩內(nèi)容