享元模式(Flyweight Pattern)是一种结构型设计模式,用于减少对象的创建数量,避免大量相似对象的内存占用。它通过共享对象来有效支持大量的细粒度对象,尤其是在需要大量类似对象的情况下,享元模式可以显著节省内存。
享元模式通过将相同或相似的对象共享来节省内存,尤其适用于那种大量相似对象的场景。例如,在绘图软件中,每个图形(如圆形、方形等)都可能有颜色、大小等不同的属性。享元模式可以将共享的部分提取出来,将不变的部分共享,而将变化的部分放入外部的状态中。
+-------------------+
| Flyweight |<-----------------------+
+-------------------+ |
| - sharedState | |
| + operation() | |
+-------------------+ |
^ |
| |
+------------------------+ |
| ConcreteFlyweight | |
+------------------------+ |
| - sharedState | |
| + operation() | |
+------------------------+ |
^ |
| |
+--------------------------+ |
| UnsharedConcreteFlyweight|-----------------+
+--------------------------+
| - uniqueState |
| + operation() |
+--------------------------+以 棋盘游戏 为例,假设我们有大量的棋子,每个棋子都需要设置颜色和类型。享元模式可以减少内存使用,避免重复创建相同类型和颜色的棋子对象。
// 享元角色:Flyweight(享元类)
interface ChessPiece {
void display(String position);
}
// 具体享元角色:ConcreteFlyweight(具体享元类)
class ConcreteChessPiece implements ChessPiece {
private String type; // 棋子的类型
public ConcreteChessPiece(String type) {
this.type = type;
}
@Override
public void display(String position) {
System.out.println("棋子类型:" + type + ", 位置:" + position);
}
}
// 非共享享元角色:UnsharedConcreteFlyweight(非共享享元类)
class UnsharedConcreteChessPiece implements ChessPiece {
private String type;
private String color; // 棋子的颜色(非共享部分)
public UnsharedConcreteChessPiece(String type, String color) {
this.type = type;
this.color = color;
}
@Override
public void display(String position) {
System.out.println("棋子类型:" + type + ", 颜色:" + color + ", 位置:" + position);
}
}
// 享元工厂:FlyweightFactory(享元工厂)
class ChessPieceFactory {
private Map<String, ChessPiece> chessPieceMap = new HashMap<>();
public ChessPiece getChessPiece(String type) {
ChessPiece piece = chessPieceMap.get(type);
if (piece == null) {
piece = new ConcreteChessPiece(type); // 如果工厂中没有该类型的棋子,就创建一个新的
chessPieceMap.put(type, piece);
System.out.println("创建新棋子:类型 " + type);
}
return piece;
}
}
public class FlyweightPatternExample {
public static void main(String[] args) {
// 享元工厂
ChessPieceFactory chessPieceFactory = new ChessPieceFactory();
// 棋盘上的棋子
ChessPiece whitePawn = chessPieceFactory.getChessPiece("兵");
whitePawn.display("A1");
ChessPiece blackKnight = chessPieceFactory.getChessPiece("马");
blackKnight.display("B2");
ChessPiece whitePawn2 = chessPieceFactory.getChessPiece("兵");
whitePawn2.display("A2");
// 非共享棋子
ChessPiece blackQueen = new UnsharedConcreteChessPiece("皇后", "黑色");
blackQueen.display("D1");
}
}display 方法。享元模式通过对象共享,减少了大量相似对象的内存开销,适用于大规模对象共享的场景。它通过将共享部分提取到外部并由享元工厂管理来优化内存使用。享元模式特别适合内存有限且需要处理大量细粒度对象的场景。
如果您有任何问题或建议,欢迎留言讨论。