设计模式学习笔记——享元(Flyweight)模式
@(设计模式)[设计模式, 享元模式, flyweight]
基本介绍
享元模式适用于需要new
大量对象的情况。通过共享实例的方式避免new
出实例,浪费资源。
在使用享元模式的时候要注意,当共享实例修改时,将会影响使用该实例的多处地方,所以使用前需要斟酌,什么类需要使用享元模式。
享元案例
类图
实现代码
BigChar类
package com.pc.flyweight.example;
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
/**
* 大字符类
* Created by Switch on 2017/3/31.
*/
public class BigChar {
/**
* 字符名称
*/
private char charname;
/**
* 大型字符对应的字符串(由'#' '.' '\n'组成)
*/
private String fontdata;
/**
* 构造方法,设置字符名称,并初始化数据
*
* @param charname 字符名称
*/
public BigChar(char charname) {
this.charname = charname;
try {
BufferedReader reader = new BufferedReader(new FileReader(System.getProperty("user.dir")
+ "/src/main/java/com/pc/flyweight/example/char/big" + charname + ".txt"));
String line;
StringBuffer buf = new StringBuffer();
while ((line = reader.readLine()) != null) {
buf.append(line);
buf.append("\n");
}
reader.close();
this.fontdata = buf.toString();
} catch (IOException e) {
this.fontdata = charname + "?\n";
}
}
/**
* 显示大型字符
*/
public void print() {
System.out.print(fontdata);
}
}
BigCharFactory类
package com.pc.flyweight.example;
import java.util.HashMap;
import java.util.Map;
/**
* 大字符工厂类
* Created by Switch on 2017/3/31.
*/
public final class BigCharFactory {
/**
* 管理已经生成的BigChar的实例
*/
private Map<String, BigChar> pool = new HashMap<>();
/**
* 唯一实例
*/
private static BigCharFactory instance = new BigCharFactory();
/**
* 获取实例
*
* @return 实例
*/
public static BigCharFactory getInstance() {
return instance;
}
private BigCharFactory() {
}
/**
* 生成(共享)BigChar类的实例
*
* @param charname 字符名
* @return 大字符对象
*/
public synchronized BigChar getBigChar(char charname) {
BigChar bc = pool.get("" + charname);
if (bc == null) {
bc = new BigChar(charname);
pool.put("" + charname, bc);
}
return bc;
}
}
BigString类
package com.pc.flyweight.example;
/**
* 大字符串
* Created by Switch on 2017/3/31.
*/
public class BigString {
/**
* 大字符数组
*/
private BigChar[] bigChars;
/**
* 构造方法,传入字符串
*
* @param string 字符串
*/
public BigString(String string) {
bigChars = new BigChar[string.length()];
BigCharFactory factory = BigCharFactory.getInstance();
for (int i = 0; i < bigChars.length; i++) {
bigChars[i] = factory.getBigChar(string.charAt(i));
}
}
/**
* 显示
*/
public void print() {
for (int i = 0; i < bigChars.length; i++) {
bigChars[i].print();
}
}
}
测试类
package com.pc.flyweight.example.test;
import com.pc.flyweight.example.BigString;
import org.junit.Test;
/**
* BigString Tester.
*
* @author Switch
* @version 1.0
*/
public class BigStringTest {
/**
* 测试享元模式
*/
@Test
public void testBigString() {
BigString bigString = new BigString("123-456.");
bigString.print();
}
}
运行结果
......##........
..######........
......##........
......##........
......##........
......##........
..##########....
................
....######......
..##......##....
..........##....
......####......
....##..........
..##............
..##########....
................
....######......
..##......##....
..........##....
......####......
..........##....
..##......##....
....######......
................
................
................
................
................
..##########....
................
................
................
........##......
......####......
....##..##......
..##....##......
..##########....
........##......
......######....
................
..##########....
..##............
..##............
..########......
..........##....
..##......##....
....######......
................
....######......
..##......##....
..##............
..########......
..##......##....
..##......##....
....######......
................
.?
享元模式中的角色
Flyweight(轻量级)
按照通常方式编写程序会导致程序变重,所以如果能够共享实例会比较好,而Flyweight
角色表示的就是那些实例会被共享的类。在案例中,由BigChar
类扮演此角色。
FlyweightFactory(轻量级工厂)
FlyweightFactory
角色是生成Flyweight
角色的工厂。在工厂中生成Flyweight
角色可以实现共享实例。在案例中,由BigCharFactory
类扮演此角色。
Client(请求者)
Client
角色使用FlyweightFactory
角色来生成Flyweight
角色。在案例中,由BigString
类扮演此角色。
类图
GitHub:DesignPatternStudy
——————参考《图解设计模式》