只生成一个对象实例的特殊类

特点:

  • 无法从外部实例化

使用场景:

  • 任务管理器,因为不能同时打开两个任务管理器
  • 回收站,在使用windows过程中,回收站一直运行维护一个唯一的实例
  • 网站计数器,一般也是采用单例模式实现,否则难以同步
  • 应用程序的日志应用
  • Web应用的配置对象的读取,Laravel 读取 .env 文件也是使用的单例
  • 数据库连接池
  • ……

Ply.png

  1. class Preferences
  2. {
  3. private array $props = [];
  4. private static $instance;
  5. private function __construct(){}
  6. private function __clone(){}
  7. public static function getInstance(): self
  8. {
  9. if (empty(self::$instace)) {
  10. self::$instance = new self();
  11. }
  12. return self::$instance;
  13. }
  14. public function setProperty(string $key,string $val)
  15. {
  16. $this->props[$key] = $val;
  17. }
  18. public function getProperty(string $key)
  19. {
  20. return $this->props[$key];
  21. }
  22. }
  1. $instance = Preferences::getInstance();
  2. $instance->setProperty('name','jack');
  3. // 销毁实例
  4. unset($instance);
  5. // 创建新实例
  6. $prefre = Preferences::getInstance();
  7. $prefre->getProperty('name'); // jack

总结:

单例和全局变量都容易被误用。因为在使用单例时,依赖关系隐藏于方法后。没有体现在方法签名中。这使得我们在开发时难以跟踪系统中的依赖关系。因此,应当小心谨慎地使用单例类。