天天看点

Java设计模式-结构型-享元模式

在工厂模式的代码中,我们不停的生成的对象,每个对象都是全新的,并在占用了部分的内存,而往往很多的对象内容都是相同的,也就是说可以共用的。享元模式也正是为了解决这种资源上的浪费而提出来的。

那么怎么样才能做到共享细粒度的对象呢?参考GoF提供的图片:

Java设计模式-结构型-享元模式

其中我觉得最关键的就是享元工厂角色中HashMap,他保存了每个实例化后的对象并使用key-value的形式保存起来。当遇到相同的key时候,直接获取内存的对象,而不用再重新创建。

图中可以这样被重复使用的就是享元角色,而没有参与参与对象保存的就是非享元角色。这样的形式是否很类似Java项目中Session之类呢。看如下代码:

//享元工厂角色
package com.henry.designModel.flyweight;

import java.util.HashMap;
import java.util.Map;

public class SessionFactory {

    private Map<String, Session> sessions = new HashMap<>();

    public Session getSession(String key) {
        Session session = sessions.get(key);
        if(session == null) {
            System.out.println("未存在,创建新的");
            session = new ObjectSession(key);
            sessions.put(key, session);
        } else {
            System.out.println("已存在,直接使用");
        }
        return session;
    }

    public void setSessions(HashMap<String, Session> sessions) {
        this.sessions = sessions;
    }
}


//享元角色抽象
package com.henry.designModel.flyweight;

public interface Session {

    public User getUser(String name);

}

//具体享元角色
package com.henry.designModel.flyweight;

public class ObjectSession implements Session {

    private String key;

    public ObjectSession(String key) {
        this.key = key;
    }

    @Override
    public User getUser(String name) {
        System.out.println("获取" + name + "对象");
        return new User(name);
    }

    public String getKey() {
        return key;
    }

    public void setKey(String key) {
        this.key = key;
    }
}

//非享元角色
package com.henry.designModel.flyweight;

public class User {

    private String name;

    public User(String name) {
        this.name = name;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }
}

//客户类
package com.henry.designModel.flyweight;

public class Client {

    public static void main(String[] args) {
        SessionFactory factory = new SessionFactory();
        Session session0 = factory.getSession("a");
        Session session1 = factory.getSession("a");
        Session session2 = factory.getSession("a");

        User user0 = session0.getUser("henry");
        User user1 = session1.getUser("ivy");
        User user2 = session2.getUser("theodore");
    }

}
           

执行客户类的结果如下:

Java设计模式-结构型-享元模式

在第二次和第三次的session获取操作中,已经不再创建新的session对象了。

继续阅读