简介
享元模式更常见的叫法是缓存或 cache,一个对象只创立一次,之后始终复用这一对象。
跟单例不同在于,单例是全局只有惟一一个对象,所有人一起用同一个对象,且该对象是提前预设好的,不能定制。
而享元则能够依据参数不同创立出不同的实例,不过实例一旦创立就只保留一份,之后再次创立雷同参数的实例则返回该对象,供所有援用的中央应用,援用方之间共享同一份享元实例的数据。
过程有点像定制化的单例模式。
角色
Flyweight 享元类
定制化的业务实体,依据不同须要可能定制不同的享元类,但一旦创立出一个享元类,当前都复用这一个类
FlyweightFactory 享元工厂类
用来创立和缓存享元实体的中央
类图
代码
class Flyweight{ private $sharedState; public function __construct($sharedState) { $this->sharedState = $sharedState; } public function operation($uniqueState): void { $s = json_encode($this->sharedState); $u = json_encode($uniqueState); echo "Flyweight: Displaying shared ($s) and unique ($u) state.\n"; }}class FlyweightFactory{ private $flyweights = []; public function __construct(array $initialFlyweights) { foreach ($initialFlyweights as $state) { $this->flyweights[$this->getKey($state)] = new Flyweight($state); } } private function getKey(array $state): string { ksort($state); return implode("_", $state); } public function getFlyweight(array $sharedState): Flyweight { $key = $this->getKey($sharedState); if (!isset($this->flyweights[$key])) { echo "FlyweightFactory: Can't find a flyweight, creating new one.\n"; $this->flyweights[$key] = new Flyweight($sharedState); } else { echo "FlyweightFactory: Reusing existing flyweight.\n"; } return $this->flyweights[$key]; } public function listFlyweights(): void { $count = count($this->flyweights); echo "\nFlyweightFactory: I have $count flyweights:\n"; foreach ($this->flyweights as $key => $flyweight) { echo $key . "\n"; } }}$factory = new FlyweightFactory([ ["Chevrolet", "Camaro2018", "pink"], ["Mercedes Benz", "C300", "black"], ["Mercedes Benz", "C500", "red"], ["BMW", "M5", "red"], ["BMW", "X6", "white"],]);$factory->listFlyweights();function addCarToPoliceDatabase( FlyweightFactory $ff, $plates, $owner, $brand, $model, $color) { echo "\nClient: Adding a car to database.\n"; $flyweight = $ff->getFlyweight([$brand, $model, $color]); $flyweight->operation([$plates, $owner]);}addCarToPoliceDatabase($factory, "CL234IR", "James Doe", "BMW", "M5", "red");addCarToPoliceDatabase($factory, "CL234IR", "James Doe", "BMW", "X1", "red");$factory->listFlyweights();
output:
FlyweightFactory: I have 5 flyweights:Chevrolet_Camaro2018_pinkMercedes Benz_C300_blackMercedes Benz_C500_redBMW_M5_redBMW_X6_whiteClient: Adding a car to database.FlyweightFactory: Reusing existing flyweight.Flyweight: Displaying shared (["BMW","M5","red"]) and unique (["CL234IR","James Doe"]) state.Client: Adding a car to database.FlyweightFactory: Can't find a flyweight, creating new one.Flyweight: Displaying shared (["BMW","X1","red"]) and unique (["CL234IR","James Doe"]) state.FlyweightFactory: I have 6 flyweights:Chevrolet_Camaro2018_pinkMercedes Benz_C300_blackMercedes Benz_C500_redBMW_M5_redBMW_X6_whiteBMW_X1_red
本文由mdnice多平台公布