CTO:不要在Java代碼中寫 set/get 方法了照瘾,逮一次罰款...

image.png

前言

what?你的 Java 代碼中還充斥著大量的 set/get 方法丧慈?

我們?cè)趧傞_始學(xué)習(xí) Java 語(yǔ)言的時(shí)候講過(guò)析命,面向?qū)ο蟮娜筇卣骶褪欠庋b,繼承逃默,和多態(tài)鹃愤。在 Java 中,要保證封裝性完域,需要將成員變量私有化昼浦,對(duì)外提供 set/get 方法來(lái)訪問(wèn),雖然現(xiàn)在的 IDE筒主,像 eclipse关噪,IDEA都提供了快捷鍵鸟蟹,來(lái)生成 set/get 方法,但是在做項(xiàng)目的時(shí)候使兔,一個(gè) JavaBean 往往會(huì)有很多的成員變量建钥,一個(gè)變量對(duì)應(yīng)兩個(gè)方法,如果有10幾個(gè)成員變量虐沥,那么會(huì)對(duì)應(yīng)20多個(gè)方法熊经,也許還要去寫構(gòu)造器、equals 等方法欲险,而且需要維護(hù)镐依。這樣一來(lái),會(huì)使代碼變得非常冗余天试,這些顯得很冗長(zhǎng)也沒(méi)有太多技術(shù)含量槐壳,一旦修改屬性,就容易出現(xiàn)忘記修改對(duì)應(yīng)方法的失誤喜每。

我在看大佬的項(xiàng)目的源碼的時(shí)候务唐,看到他們的代碼中都沒(méi)有 set/get 方法,取而代之的是在 JavaBean 上標(biāo)注的注解带兜,我感到非常的好奇枫笛,原來(lái)他們是用了一種叫做 Lombok 的插件,便去詳細(xì)了解了這個(gè)插件刚照。

Lombok背景介紹

官方介紹如下:

Project Lombok makes java a spicier language by adding 'handlers' that know how to build and compile simple, boilerplate-free, not-quite-java code.

大致意思是 Lombok 通過(guò)增加一些“處理程序”刑巧,可以讓 Java 變得簡(jiǎn)潔、快速无畔。

Lombok使用方法

Lombok 能通過(guò)注解的方式海诲,在編譯時(shí)自動(dòng)為屬性生成構(gòu)造器、getter/setter檩互、equals特幔、hashcode、toString 方法闸昨。出現(xiàn)的神奇就是在源碼中沒(méi)有 getter 和 setter 方法蚯斯,但是在編譯生成的字節(jié)碼文件中有 getter 和 setter 方法。這樣就省去了手動(dòng)重建這些代碼的麻煩饵较,使代碼看起來(lái)更簡(jiǎn)潔些拍嵌。

Lombok 的使用跟引用 jar 包一樣,可以在官網(wǎng)(https://projectlombok.org/download)下載 jar 包循诉,也可以使用 maven 添加依賴:

<dependency>
  <groupId>org.projectlombok</groupId>

    <artifactId>lombok</artifactId>

    <version>1.18.10</version>

    <scope>provided</scope>

</dependency>

注意:

第一次使用 Lombok 插件需要做如下幾步配置

  • 將 Lombok 插件安裝到 IDEA
file -> setting

選中 Plugins横辆,搜索 Lombok,點(diǎn)擊 Install

  • 選擇默認(rèn)的編譯方式為 javac茄猫,因?yàn)?eclipse 是不支持 Lombok 的編譯方式的狈蚤,javac 支持 Lombok 的編譯方式困肩。

  • 打開注解生成器 Enable annotation processing

再次注意:

IntelliJ IDEA 2019.2(也就是我用的版本)默認(rèn)是不支持 Lombok 插件的,需要去

https://plugins.jetbrains.com/plugin/6317-lombok/versions

下載對(duì)應(yīng)版本的插件脆侮,然后手動(dòng)引入锌畸,在 IDEA 中選擇 File -> Setting -> plugins 找到 Install Plugin from Disk…(注意版本不同位置可能有所差異)

接下來(lái)我們來(lái)分析 Lombok 中注解的具體用法

@Data

@Data 注解在類上,會(huì)為類的所有屬性自動(dòng)生成 setter/getter靖避、equals潭枣、canEqual、hashCode幻捏、toString 方法盆犁,如為 final 屬性,則不會(huì)為該屬性生成 setter 方法篡九。

比如我們寫一個(gè)學(xué)生類

@Data
public class Student {

    private String name;

    private Integer age;

    private Integer id;

    private String major;

}

這樣就可以調(diào)用 set/get 方法了谐岁。

@Getter/@Setter

如果覺得@Data 太過(guò)殘暴(因?yàn)锧Data 集合了@ToString、@EqualsAndHashCode瓮下、@Getter/@Setter翰铡、@RequiredArgsConstructor 的所有特性)不夠精細(xì)钝域,可以使用@Getter/@Setter 注解讽坏,此注解在屬性上,可以為相應(yīng)的屬性自動(dòng)生成 set/get 方法例证。

public class Student {
  @Setter private String name;

    private Integer age;

    private Integer id;

    private String major;

    public static void main(String[] args) {

        Student stu = new Student();

        stu.setName("Mr.ml");

    }
}

@NonNull

該注解用在屬性或構(gòu)造器上路呜,Lombok 會(huì)生成一個(gè)非空的聲明,可用于校驗(yàn)參數(shù)织咧,能幫助避免空指針胀葱。

public class Student {
  @Setter private String name;

    private Integer age;

    private Integer id;

    private String major;

    public Student(@NonNull String name) {

        this.name = name;

    }

}

@Cleanup

該注解能幫助我們自動(dòng)調(diào)用 close() 方法,很大的簡(jiǎn)化了代碼笙蒙。

public class CleanupExample {
  public static void main(String[] args) throws IOException {

        @Cleanup InputStream in = new FileInputStream(args[0]);

        @Cleanup OutputStream out = new FileOutputStream(args[1]);

        byte[] b = new byte[10000];

        while (true) {

            int r = in.read(b);

            if (r == -1) break;

            out.write(b, 0, r);

        }

    }

}

@EqualsAndHashCode

默認(rèn)情況下抵屿,會(huì)使用所有非靜態(tài)(non-static)和非瞬態(tài)(non-transient)屬性來(lái)生成 equals 和 hashCode,也能通過(guò) exclude 注解來(lái)排除一些屬性捅位。

@EqualsAndHashCode(exclude={"id", "shape"})
public class EqualsAndHashCodeExample {

    private transient int transientVar = 10;

    private String name;

    private double score;

    private Shape shape = new Square(5, 10);

    private String[] tags;

    private int id;

    public String getName() {

        return this.name;

    }

    @EqualsAndHashCode(callSuper=true)

    public static class Square extends Shape {

        private final int width, height;

        public Square(int width, int height) {

            this.width = width;

            this.height = height;

        }

    }

}

@ToString

類使用@ToString 注解轧葛,Lombok 會(huì)生成一個(gè) toString() 方法,默認(rèn)情況下艇搀,會(huì)輸出類名、所有屬性(會(huì)按照屬性定義順序),用逗號(hào)來(lái)分割州胳。

通過(guò)將 includeFieldNames 參數(shù)設(shè)為 true客峭,就能明確的輸出 toString() 屬性。這一點(diǎn)是不是有點(diǎn)繞口矩屁,通過(guò)代碼來(lái)看會(huì)更清晰些辟宗。

@ToString(exclude="id")
public class ToStringExample {

    private static final int STATIC_VAR = 10;

    private String name;

    private Shape shape = new Square(5, 10);

    private String[] tags;

    private int id;

    public String getName() {

        return this.getName();

    }

    @ToString(callSuper=true, includeFieldNames=true)

    public static class Square extends Shape {

        private final int width, height;

        public Square(int width, int height) {

            this.width = width;

            this.height = height;

        }

    }

}

@NoArgsConstructor, @RequiredArgsConstructor and @AllArgsConstructor

無(wú)參構(gòu)造器爵赵、部分參數(shù)構(gòu)造器、全參構(gòu)造器慢蜓。Lombok沒(méi)法實(shí)現(xiàn)多種參數(shù)構(gòu)造器的重載亚再。

@RequiredArgsConstructor(staticName = "of")
@AllArgsConstructor(access = AccessLevel.PROTECTED)

public class ConstructorExample<T> {

    private int x, y;

    @NonNull private T description;

    @NoArgsConstructor

    public static class NoArgsExample {

        @NonNull private String field;

    }

}
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市晨抡,隨后出現(xiàn)的幾起案子氛悬,更是在濱河造成了極大的恐慌,老刑警劉巖耘柱,帶你破解...
    沈念sama閱讀 218,755評(píng)論 6 507
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件如捅,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡调煎,警方通過(guò)查閱死者的電腦和手機(jī)镜遣,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,305評(píng)論 3 395
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)士袄,“玉大人悲关,你說(shuō)我怎么就攤上這事÷α” “怎么了寓辱?”我有些...
    開封第一講書人閱讀 165,138評(píng)論 0 355
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)赤拒。 經(jīng)常有香客問(wèn)我秫筏,道長(zhǎng),這世上最難降的妖魔是什么挎挖? 我笑而不...
    開封第一講書人閱讀 58,791評(píng)論 1 295
  • 正文 為了忘掉前任这敬,我火速辦了婚禮,結(jié)果婚禮上蕉朵,老公的妹妹穿的比我還像新娘崔涂。我一直安慰自己,他們只是感情好始衅,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,794評(píng)論 6 392
  • 文/花漫 我一把揭開白布冷蚂。 她就那樣靜靜地躺著,像睡著了一般觅闽。 火紅的嫁衣襯著肌膚如雪帝雇。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,631評(píng)論 1 305
  • 那天蛉拙,我揣著相機(jī)與錄音尸闸,去河邊找鬼。 笑死,一個(gè)胖子當(dāng)著我的面吹牛吮廉,可吹牛的內(nèi)容都是我干的苞尝。 我是一名探鬼主播,決...
    沈念sama閱讀 40,362評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼宦芦,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼宙址!你這毒婦竟也來(lái)了?” 一聲冷哼從身側(cè)響起调卑,我...
    開封第一講書人閱讀 39,264評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤抡砂,失蹤者是張志新(化名)和其女友劉穎,沒(méi)想到半個(gè)月后恬涧,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體注益,經(jīng)...
    沈念sama閱讀 45,724評(píng)論 1 315
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,900評(píng)論 3 336
  • 正文 我和宋清朗相戀三年溯捆,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了丑搔。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 40,040評(píng)論 1 350
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡提揍,死狀恐怖啤月,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情劳跃,我是刑警寧澤谎仲,帶...
    沈念sama閱讀 35,742評(píng)論 5 346
  • 正文 年R本政府宣布,位于F島的核電站售碳,受9級(jí)特大地震影響强重,放射性物質(zhì)發(fā)生泄漏绞呈。R本人自食惡果不足惜贸人,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,364評(píng)論 3 330
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望佃声。 院中可真熱鬧艺智,春花似錦、人聲如沸圾亏。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,944評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)志鹃。三九已至夭问,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間曹铃,已是汗流浹背缰趋。 一陣腳步聲響...
    開封第一講書人閱讀 33,060評(píng)論 1 270
  • 我被黑心中介騙來(lái)泰國(guó)打工, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人秘血。 一個(gè)月前我還...
    沈念sama閱讀 48,247評(píng)論 3 371
  • 正文 我出身青樓味抖,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親灰粮。 傳聞我的和親對(duì)象是個(gè)殘疾皇子仔涩,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,979評(píng)論 2 355

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