Dart单例模式

本文最后更新于:3 个月前

一、几个知识点

  • 当使用factory关键词修饰构造函数时,这个构造函数不会创建类的实例
  • 使用new语句来构造一个类,构造函数的名字可能是ClassName,也可以是ClassName.otherName,关键字new可以省略
  • Dart没有关键字publicprotectedprivate,如果标识符以下划线_开头,则它相对于库是私有的,每个.dart文件都是一个库

二、代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25

class SingletonClass {
// 单例中的参数
String params1;

// 静态变量
static SingletonClass _instance;
// 使用factory修饰无名构造函数,不创建新的实例,直接导向sharedInstance方法,也可以直接删除无名构造函数的方法
factory SingletonClass() {
return SingletonClass.sharedInstance();
}
// 指定私有构造函数作为唯一初始化入口
SingletonClass._init();
// 再提供工厂单例构造函数,用来标识该类为单例类
factory SingletonClass.sharedInstance() {
if (_instance == null) {
// 调用私有构造函数创建实例,并赋值给静态变量
_instance = SingletonClass._init();
// 可以在此处设置参数默认值
_instance.params1 = '1';
}
return _instance;
}
}

说明:

  1. 单例需要在整个APP内存中保持只被创建一次,所以需要使用静态变量
  2. 为了标识某个类为单例类,增加可读性,所以建议使用统一格式或者统一关键字的有名构造函数,无名构造函数可以不提供
  3. 提供私有构造函数来初始化实例对象,防止其他库直接访问该初始化方法

三、使用单例进行通知

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57

typedef void NotiCallback<T>(params);

class EventBus {
// 静态变量
static EventBus _instance;
// 默认无名构造方法
factory EventBus() {
return EventBus.sharedInstance();
}
// 私有构造方法
EventBus._init();
// 单例对外提供的构造方法
factory EventBus.sharedInstance() {
if (_instance == null) {
_instance = EventBus._init();
}
return _instance;
}

// 保存callback的参数
Map<String, NotiCallback> _notiMap = Map();

// 对外提供添加,删除,触发的方法
// 添加
void add<String, NotiCallback>(eventName, callback) {
if (eventName == null) {
return;
}
if (eventName.length == 0) {
return;
}
_notiMap[eventName] = callback;
}
// 移除
void remove<String, NotiCallback>(eventName, callback) {
if (eventName == null) {
return;
}
if (eventName.length == 0) {
return;
}
_notiMap[eventName] = null;
}
// 触发
void emit<String, T>(eventName, params) {
if (eventName == null) {
return;
}
if (eventName.length == 0) {
return;
}
NotiCallback callback = _notiMap[eventName];
callback(params);
}
}

使用callback进行传参,在单例中一对一保存callback,如果是一对多的场景,可在单例中保存list数据