Enum的簡(jiǎn)介
Enum是計(jì)算機(jī)編程語(yǔ)言中的一種數(shù)據(jù)類型唉铜。枚舉類型`
枚舉類型很早就在計(jì)算機(jī)語(yǔ)言中存在了烙心,主要被用來(lái)將一組相似的值包含進(jìn)一種類型中,這種類型的名稱被定義成獨(dú)一無(wú)二的類型描述符贝或,這就是枚舉類型芝发。
在java語(yǔ)言中,枚舉類型是一個(gè)完整功能的類,允許開(kāi)發(fā)者給枚舉類型添加方法和屬性耳璧,同時(shí)也可以提供接口成箫。同時(shí)Java也為Enum提供了高質(zhì)量的實(shí)現(xiàn),比如comparable和Serializable接口.
- 其中:Comparable 是排序接口旨枯,如果一個(gè)Java類有這個(gè)接口蹬昌,那么只能說(shuō)明這個(gè)類支持排序。即然實(shí)現(xiàn)Comparable接口的類支持排序攀隔,假設(shè)現(xiàn)在存在“實(shí)現(xiàn)Comparable接口的類的對(duì)象的List列表(或數(shù)組)皂贩,則該List列表(或數(shù)組)可以通過(guò) Collections.sort(或 Arrays.sort)進(jìn)行排序±バ冢“實(shí)現(xiàn)Comparable接口的類的對(duì)象”可以用作“有序映射(如TreeMap)”中的鍵或“有序集合(TreeSet)”中的元素明刷,而不需要指定比較器。 Serializable接口的對(duì)象轉(zhuǎn)換成一個(gè)字符序列筹煮,并能夠在以后將這個(gè)字節(jié)序列完全恢復(fù)為原來(lái)的對(duì)象遮精。而且這個(gè)過(guò)程是可以通過(guò)網(wǎng)絡(luò)完成的,也就是說(shuō)序列化機(jī)制能夠自動(dòng)彌補(bǔ)不同操作系統(tǒng)之間差異败潦。*
Enum的定制
通過(guò)類的定義本冲,可以給Enum一些復(fù)雜的功能,例如下面代碼給Enum增加屬性:
public enum DrinkEnum{
1. // 酒
2. Wine("a cup of wine ");
3. //橙汁
4. Oragen_Juice("a cup of oragen juice")
5. //Enum對(duì)象的drink_class屬性
6. private String drink_class;
7. //枚舉對(duì)象構(gòu)造函數(shù)
8. private DrinkEnum(String drink){
9. this.drink_class=drink;
10. }
11. //枚舉對(duì)象的drink_class屬性
12. public String getDrink(){
13. return this.drink_class;
14. }
Enum的一些坑
1 Enum 不支持public和protected修飾符的構(gòu)造方法劫扒,因此構(gòu)造函數(shù)一定要是private或者friendly的檬洞,這也就約束了枚舉對(duì)象是無(wú)法在程序中通過(guò)直接調(diào)用構(gòu)造函數(shù)進(jìn)行初始化的。
2 Enum的值是通過(guò)運(yùn)行期構(gòu)造出來(lái)的對(duì)象表示的沟饥,因此在集群環(huán)境下添怔,每個(gè)jvm構(gòu)造出同義對(duì)象,但是在做布爾運(yùn)算的時(shí)候有可能有問(wèn)題贤旷,因此要格外注意广料。在對(duì)Enum進(jìn)行比較的時(shí)候,使用值比對(duì)幼驶。
Enum的原理
在使用enum創(chuàng)建枚舉類型后艾杏,編譯器會(huì)為其生成一個(gè)對(duì)應(yīng)的枚舉類,這個(gè)類繼承與java.lang.Enum盅藻。舉例如下:
1. enum Day {
2. MONDAY, TUESDAY, WEDNESDAY,
3. THURSDAY, FRIDAY, SATURDAY, SUNDAY
4. }
編譯后會(huì)變成Day.class购桑,那么反編譯后看到如下:
1. final class Day extends Enum
2. {
3. //編譯器為我們添加的靜態(tài)的values()方法
4. public static Day[] values()
5. {
6. return (Day[])$VALUES.clone();
7. }
8. //編譯器為我們添加的靜態(tài)的valueOf()方法,注意間接調(diào)用了Enum也類的valueOf方法
9. public static Day valueOf(String s)
10. {
11. return (Day)Enum.valueOf(com/zejian/enumdemo/Day, s);
12. }
13. //私有構(gòu)造函數(shù)
14. private Day(String s, int i)
15. {
16. super(s, i);
17. }
18. //前面定義的7種枚舉實(shí)例
19. public static final Day MONDAY;
20. public static final Day TUESDAY;
21. public static final Day WEDNESDAY;
22. public static final Day THURSDAY;
23. public static final Day FRIDAY;
24. public static final Day SATURDAY;
25. public static final Day SUNDAY;
26. private static final Day $VALUES[];
27. static
28. {
29. //實(shí)例化枚舉實(shí)例
30. MONDAY = new Day("MONDAY", 0);
31. TUESDAY = new Day("TUESDAY", 1);
32. WEDNESDAY = new Day("WEDNESDAY", 2);
33. THURSDAY = new Day("THURSDAY", 3);
34. FRIDAY = new Day("FRIDAY", 4);
35. SATURDAY = new Day("SATURDAY", 5);
36. SUNDAY = new Day("SUNDAY", 6);
37. $VALUES = (new Day[] {
38. MONDAY, TUESDAY, WEDNESDAY, THURSDAY, FRIDAY, SATURDAY, SUNDAY
39. });
40. }
41. }
可以看到氏淑,編譯后生成一個(gè)final類勃蜘,同時(shí)前面的七個(gè)日期定義成七個(gè)類型。同時(shí)還有兩個(gè)靜態(tài)方法假残,分別是values()和 valueOf()缭贡,MONDAY枚舉類型對(duì)應(yīng)public static final Day MONDAY;,values()方法的作用就是獲取枚舉類中的所有變量,并作為數(shù)組返回匀归,而valueOf(String name)方法與Enum類中的valueOf方法的作用類似根據(jù)名稱獲取枚舉變量坑资,只不過(guò)編譯器生成的valueOf方法更簡(jiǎn)潔些只需傳遞一個(gè)參數(shù)。由于values()方法是由編譯器插入到枚舉類中的static方法穆端,所以如果我們將枚舉實(shí)例向上轉(zhuǎn)型為Enum袱贮,那么values()方法將無(wú)法被調(diào)用,因?yàn)镋num類中并沒(méi)有values()方法体啰,valueOf()方法也是同樣的道理攒巍。
final變量經(jīng)常和static關(guān)鍵字一起使用,作為常量荒勇。final類通常功能是完整的柒莉,不允許被繼承。
因此枚舉類型沽翔,在調(diào)用中如果對(duì)內(nèi)部變量使用了set函數(shù)兢孝,那么就是對(duì)一個(gè)常量進(jìn)行了上set操作,也就會(huì)導(dǎo)致所有調(diào)用的地方的值都發(fā)生了變化仅偎。
如果對(duì)軟件測(cè)試跨蟹、接口測(cè)試、自動(dòng)化測(cè)試橘沥、性能測(cè)試窗轩、LR腳本開(kāi)發(fā)、面試經(jīng)驗(yàn)交流座咆。感興趣可以175317069痢艺,群內(nèi)會(huì)有不定期的發(fā)放免費(fèi)的資料鏈接,這些資料都是從各個(gè)技術(shù)網(wǎng)站搜集介陶、整理出來(lái)的堤舒,如果你有好的學(xué)習(xí)資料可以私聊發(fā)我,我會(huì)注明出處之后分享給大家哺呜。
EnumSet和EnumMap
EnumSet
EnumSet是一個(gè)針對(duì)枚舉類型的高性能Set接口實(shí)現(xiàn)舌缤,但是在其中裝入的枚舉類型必須是同類型的,在EnumSet中通過(guò)bit-vector實(shí)現(xiàn)弦牡,也就是一個(gè)long型。EnumSet支持在遍歷漂羊。
1. for (WeekDayEnum day:EnumSet.range(WeekDayEnum.Mon,WeekDayEnum.Sun)){
2. System.out.println(day)
3. }
同時(shí)EnumSet還提供了一個(gè)獲取子集的方法:
1. EnumSet <WeekDayEnum> JobDays = EnumSet.of(WeekDayEnum.Mon,WeekDayEnum.Fri);
EnumMap
EnumMap是一個(gè)高性能的Map接口實(shí)現(xiàn)驾锰,主要管理用枚舉做Key-Value的關(guān)系,內(nèi)部是通過(guò)數(shù)組方式實(shí)現(xiàn)的走越。
1. private static Map<WeekDayEnum椭豫,RainbowClolor> schema = new EnumMap<WeekDayEnum.values()[i],RainbowClolor.values()[i]>(WeekDatEnum.class);