想必对于大部分的开发来说,这是咱们接触最多的设计模式之一了。
单例模式(Singleton Pattern)理念:
唯一实例: 单例模式保证了某个类只有一个实例存在。这意味着无论何时何地调用该类,只会返回同一个对象实例。
全局访问: 提供一个全局访问点来获取该唯一实例。通常通过一个静态方法或属性来实现。
延迟实例化: 单例模式通常支持延迟实例化,即在第一次请求时创建实例,以节省资源。
设计思路:
私有构造函数: 将类的构造函数设为私有,以防止外部通过普通构造方法创建实例。
静态实例: 使用静态变量存储类的唯一实例。
静态方法: 提供一个公共的静态方法或属性,返回该唯一实例。
代码实现:
1. 饿汉式单例
这种方式在类加载时就创建实例,线程安全,但如果实例初始化开销大且不一定会用到,会造成资源浪费。
class Singleton {
//私有构造函数
Singleton._privateConstructor();
// 静态实例
static final Singleton instance = Singleton._privateConstructor();
// 内部方法
void printHello() {
print('Hello');
}
}
//调用方式
Singleton.instance.printHello();
2. 懒汉式单例
这种方式在第一次使用时才创建实例,延迟加载。
class SingletonLazy {
//私有构造
SingletonLazy._privateConstructor();
//静态实例
static SingletonLazy? _instance;
//获取实列方法
static SingletonLazy getInstance() {
if (_instance == null) {
_instance = SingletonLazy._privateConstructor();
}
return _instance!;
}
}
也可以通过dart中的工厂类来创建懒汉式
class SingletonFactory {
// 私有构造函数
SingletonFactory._privateConstructor();
// 静态变量来存储唯一实例
static SingletonFactory? _instance;
// 工厂构造函数
factory SingletonFactory() {
if (_instance == null) {
_instance = SingletonFactory._privateConstructor();
}
return _instance!;
}
void someMethod() {
print('This is a method in SingletonFactory');
}
}
3.静态内部类
这种方式利用 Dart 的静态内部类特性,既实现了延迟加载,又保证了线程安全。
class Singleton {
// 私有构造函数
Singleton._privateConstructor();
// 静态内部类
static final Singleton instance = _SingletonHolder.instance;
// 内部类
static class _SingletonHolder {
static final Singleton instance = Singleton._privateConstructor();
}
}
4. 懒汉式双重检查
额~~~写java过来的人条件反射就是,单例要考虑线程安全,加锁。。。
其实在flutter中,由于Flutter是单线程模式的,很少会有多线程切换的使用场景,它的异步操作是通过Future来实现的,其内部也是通过堆栈来实现阻塞(await)和插件队列执行,理论上是线程安全的,除非你非得使用Isolates,但是Isolates一种多线程模型,每个 Isolate 拥有独立的内存空间,因此单例在不同的 Isolate 中不会共享。这意味着在 Dart 中,通常不需要担心传统意义上的多线程竞争条件。所以个人觉得,没有必要加锁考虑并发情况,非得写考虑 静态内部类