设计模式之享元模式学习理解

享元模式(Flyweight Pattern)主要用于减少创建对象的数量,以减少内存占用和提高性能。这种类型的设计模式属于结构型模式,它提供了减少对象数量从而改善应用所需的对象结构的方式。

享元模式尝试重用现有的同类对象,如果未找到匹配的对象,则创建新对象。

意图:运用共享技术有效地支持大量细粒度的对象。

主要解决:在有大量对象时,有可能会造成内存溢出,我们把其中共同的部分抽象出来,如果有相同的业务请求,直接返回在内存中已有的对象,避免重新创建。

何时使用: 1、系统中有大量对象。 2、这些对象消耗大量内存。 3、这些对象的状态大部分可以外部化。 4、这些对象可以按照内蕴状态分为很多组,当把外蕴对象从对象中剔除出来时,每一组对象都可以用一个对象来代替。 5、系统不依赖于这些对象身份,这些对象是不可分辨的。

如何解决:用唯一标识码判断,如果在内存中有,则返回这个唯一标识码所标识的对象。

关键代码:用 HashMap 存储这些对象。

应用实例: 1、JAVA 中的 String,如果有则返回,如果没有则创建一个字符串保存在字符串缓存池里面。 2、数据库的数据池。

优点:大大减少对象的创建,降低系统的内存,使效率提高。

缺点:提高了系统的复杂度,需要分离出外部状态和内部状态,而且外部状态具有固有化的性质,不应该随着内部状态的变化而变化,否则会造成系统的混乱。

使用场景: 1、系统有大量相似对象。 2、需要缓冲池的场景。

注意事项: 1、注意划分外部状态和内部状态,否则可能会引起线程安全问题。 2、这些类必须有一个工厂对象加以控制。

假设有个销售单模板的需求,每个销售人对应自己的模板不变。

销售单接口

1 /**
2  * 销售单接口
3  * @author ko
4  */
5 public interface SalesSlip {
6     void print();
7 }

设备销售单

 1 import java.math.BigDecimal;
 2 import java.util.Date;
 3 
 4 public class DeviceSalesSlip implements SalesSlip {
 5 
 6     public String salesPerson;
 7     
 8     public String title;
 9     public String address;
10     public Date date;
11     public BigDecimal salesVolume;
12     
13     public DeviceSalesSlip(String salesPerson) {
14         this.salesPerson = salesPerson;
15     }
16 
17     @Override
18     public void print() {
19         System.out.println("DeviceSalesSlip [salesPerson=" + salesPerson + ", title=" + title + ", address=" + address + ", date="
20                 + date + ", salesVolume=" + salesVolume + "]");
21     }
22 
23 
24     public void setTitle(String title) {
25         this.title = title;
26     }
27 
28 
29     public void setAddress(String address) {
30         this.address = address;
31     }
32 
33 
34     public void setDate(Date date) {
35         this.date = date;
36     }
37 
38 
39     public void setSalesVolume(BigDecimal salesVolume) {
40         this.salesVolume = salesVolume;
41     }
42 
43 }

生成销售单的工厂类

 1 import java.util.HashMap;
 2 
 3 public class SalesSlipFactory {
 4 
 5     private static final HashMap<String, SalesSlip> ssMap = new HashMap<>();
 6     
 7     public static SalesSlip getSalesSlip(String salesPerson){
 8         DeviceSalesSlip deviceSalesSlip = (DeviceSalesSlip) ssMap.get(salesPerson);
 9         if (deviceSalesSlip == null) {
10             deviceSalesSlip = new DeviceSalesSlip(salesPerson);
11             ssMap.put(salesPerson, deviceSalesSlip);
12             System.out.println("create deviceSalesSlip by person:"+salesPerson);
13         }
14         return deviceSalesSlip;
15     }
16 }

测试类

 1 public class Test {
 2 
 3     private static final String[] salesPersons = new String[]{"djii","iioi","tgyg","ssaw","qqww","nnjk"};
 4     
 5     public static void main(String[] args) {
 6         for (int i = 0; i < 6; i++) {
 7             DeviceSalesSlip deviceSalesSlip = (DeviceSalesSlip) SalesSlipFactory.getSalesSlip(salesPersons[i]);
 8             deviceSalesSlip.setTitle("test title "+i);
 9             deviceSalesSlip.setDate(new Date());
10             deviceSalesSlip.setAddress("test address "+i);
11             deviceSalesSlip.setSalesVolume(new BigDecimal(new Random().nextInt(10)));
12             deviceSalesSlip.print();
13         }
14         
15     }
16 }

运行结果

create deviceSalesSlip by person:djii
DeviceSalesSlip [salesPerson=djii, title=test title 0, address=test address 0, date=Tue Jul 11 13:40:40 CST 2017, salesVolume=9]
create deviceSalesSlip by person:iioi
DeviceSalesSlip [salesPerson=iioi, title=test title 1, address=test address 1, date=Tue Jul 11 13:40:40 CST 2017, salesVolume=9]
create deviceSalesSlip by person:tgyg
DeviceSalesSlip [salesPerson=tgyg, title=test title 2, address=test address 2, date=Tue Jul 11 13:40:40 CST 2017, salesVolume=7]
create deviceSalesSlip by person:ssaw
DeviceSalesSlip [salesPerson=ssaw, title=test title 3, address=test address 3, date=Tue Jul 11 13:40:40 CST 2017, salesVolume=2]
create deviceSalesSlip by person:qqww
DeviceSalesSlip [salesPerson=qqww, title=test title 4, address=test address 4, date=Tue Jul 11 13:40:40 CST 2017, salesVolume=6]
create deviceSalesSlip by person:nnjk
DeviceSalesSlip [salesPerson=nnjk, title=test title 5, address=test address 5, date=Tue Jul 11 13:40:40 CST 2017, salesVolume=8]
原文地址:https://www.cnblogs.com/shamo89/p/7150955.html