Westward Java design patterns learning summary (26) --- Flyweight

Disclaimer: This article is a blogger original article, shall not be reproduced without the bloggers allowed. https://blog.csdn.net/a770794164/article/details/90734451

Flyweight (Flyweight), Use sharing to support large numbers of fine-grained objects.
Westward from design patterns
Example:
Casual game developers, such as Go, backgammon, checkers, which have a large number of objects pawn, if using conventional programming object-oriented way, will have a large number of objects, so that the server is difficult to support large-scale amount of players play games, because of limited memory. If Flyweight mode, the object piece may be reduced to two examples, wherein the two different colors is not shared pieces each Flyweight class.

  1. Pawn an abstract class, metaclass Get
abstract class Chess {
	abstract void buildChess();
}
  1. Flyweight implementation class, two pieces of color noninterference
class BlackChess extends Chess {
	@Override
	void buildChess() {
		System.out.println("创建了一个黑色棋子");
	}
}

class WhiteChess extends Chess {
	@Override
	void buildChess() {
		System.out.println("创建了一个白色棋子");
	}
}
  1. Flyweight factory class
class ChessFactory {
	
	private static HashMap<String, Chess> chessMap = new HashMap<>();
	
	// 获取各个棋子
	static Chess getChess(String color) {
		if (!chessMap.containsKey(color)) {
			Chess chess = null;
			if ("白色".equals(color)) {
				chess = new WhiteChess();
			} else {
				chess = new BlackChess();
			}
			chessMap.put(color, chess);
			return chess;
		} else {
			return chessMap.get(color);
		}
	}
	
	static int getChessCount() {
		return chessMap.size();
	}
}
  1. The main program
class Test {

	public static void main(String[] args) {
		Chess white1 = ChessFactory.getChess("白色");
		Chess black1 = ChessFactory.getChess("黑色");
		Chess white2 = ChessFactory.getChess("白色");
		Chess black2 = ChessFactory.getChess("黑色");
		Chess white3 = ChessFactory.getChess("白色");
		Chess black3 = ChessFactory.getChess("黑色");
		
		white1.buildChess();
		white2.buildChess();
		white3.buildChess();
		System.out.println(white1 == white2);
		System.out.println(white2 == white3);
		
		black1.buildChess();
		black2.buildChess();
		black3.buildChess();
		System.out.println(black1 == black2);
		System.out.println(black2 == black3);
		
		System.out.println("棋子个数:" + ChessFactory.getChessCount());
	}

}
结果:
创建了一个白色棋子
创建了一个白色棋子
创建了一个白色棋子
true
true
创建了一个黑色棋子
创建了一个黑色棋子
创建了一个黑色棋子
true
true
棋子个数:2

It can be seen, although the use of factory objects created six pieces, but the actual object is only two.

Internal state and external state:
the shared element inside the object and does not change with environmental changes shared portion, the internal state may be referred to as a shared element object, and with changes in environmental changes, the state is not shared external state . In fact, to avoid a lot of overhead Flyweight pattern is very similar to the class. In programming, the class may need to generate a large amount of fine-grained to identify instances of data. If these examples can be found in addition to several parameters are substantially the same, and sometimes can be greatly reduced by the required number of instances of the class. If we can move outside those parameters class instance, when they passed in the method call, you can share a single instance of a substantial reduction in the number.

For example:
earlier example, there is only a pawn, so that multi-round game, you need to add a message board, which represents the Bureau of the game is to continue to adjust the code:

  1. Add chessboard class
class Chessboard {
	private String name;
	public Chessboard(String name) {
		this.name = name;
	}
	public String getName() {
		return name;
	}
}
  1. Flyweight class adjustment
abstract class Chess {
	abstract void buildChess(Chessboard chessboard);
}

class WhiteChess extends Chess {
	@Override
	void buildChess(Chessboard chessboard) {
		System.out.println("在棋盘:" + chessboard.getName() + " 创建了一个白色棋子");
	}
}

class BlackChess extends Chess {
	@Override
	void buildChess(Chessboard chessboard) {
		System.out.println("在棋盘:" + chessboard.getName() + " 创建了一个黑色棋子");
	}
}
  1. The main program
class Test {

	public static void main(String[] args) {
		Chess white1 = ChessFactory.getChess("白色");
		Chess black1 = ChessFactory.getChess("黑色");
		Chess white2 = ChessFactory.getChess("白色");
		Chess black2 = ChessFactory.getChess("黑色");
		Chess white3 = ChessFactory.getChess("白色");
		Chess black3 = ChessFactory.getChess("黑色");
		
		white1.buildChess(new Chessboard("对局一"));
		white2.buildChess(new Chessboard("对局二"));
		white3.buildChess(new Chessboard("对局三"));
		System.out.println(white1 == white2);
		System.out.println(white2 == white3);
		
		black1.buildChess(new Chessboard("对局四"));
		black2.buildChess(new Chessboard("对局五"));
		black3.buildChess(new Chessboard("对局六"));
		System.out.println(black1 == black2);
		System.out.println(black2 == black3);
		
		System.out.println("棋子个数:" + ChessFactory.getChessCount());
	}

}
结果:
在棋盘:对局一 创建了一个白色棋子
在棋盘:对局二 创建了一个白色棋子
在棋盘:对局三 创建了一个白色棋子
true
true
在棋盘:对局四 创建了一个黑色棋子
在棋盘:对局五 创建了一个黑色棋子
在棋盘:对局六 创建了一个黑色棋子
true
true
棋子个数:2

scenes to be used

If an application uses a large number of objects, and a large number of these objects caused when you should consider using a large storage overhead; there is the most state of the object may be outside the state, if you delete an object outside the state, you can use a relatively small number of shared objects substituent group object, then you can consider using Flyweight. But Flyweight need to maintain a list of all Flyweight record of the existing system, which itself consumes resources, in addition Flyweight makes the system more complicated. In order to share the object may need to be outside of some status, which makes complicated logic. Therefore, there should be more than enough to enjoy the object instance is available only yuan worth using Flyweight pattern.

Guess you like

Origin blog.csdn.net/a770794164/article/details/90734451