⭐️ 更多前端技术和知识点,搜索订阅号 JS 菌
订阅
- 组合模式在对象间形成树形结构;
- 组合模式中基本对象和组合对象被一致对待;
- 无须关心对象有多少层, 调用时只需在根部进行调用;
实现原理
- 创建宏任务并维护一个任务列表 list
- 创建宏任务方法 add 将 task push 到 list 中
- 创建 execute 方法循环遍历 list 中的 task 对象
- task 对象必须拥有一个名为 execute 的方法(用来在宏任务中遍历 list)
代码实现
const MacroCommand = function() {
this.lists = [] // 宏任务维护一个任务列表
}
MacroCommand.prototype.add = function(task) {
this.lists.push(task) // add 方法增加任务
}
MacroCommand.prototype.execute = function() {
for (let index = 0; index < this.lists.length; index++) {
this.lists[index].execute() // execute 方法执行任务
}
}
const command1 = new MacroCommand() // 通过 new 操作符创建任务
command1.add({
execute: () => { console.log('command1-1') }
})
command1.add({
execute: () => { console.log('command1-2') }
})
const command2 = new MacroCommand()
command2.add({
execute: () => { console.log('command2-1') }
})
command2.add({
execute: () => { console.log('command2-2') }
})
command2.add({
execute: () => { console.log('command2-3') }
})
const macroCommand = new MacroCommand() // 假定 macroCommand 为宏任务
macroCommand.add(command1) // 将其他子任务推如任务列表
macroCommand.add(command2)
macroCommand.execute() // 宏命令执行操作后,command 将依次递归执行
// command1-1
// command1-2
// command2-1
// command2-2
// command2-3
应用
扫描文件夹
文件夹下面可以为另一个文件夹也可以为文件, 我们希望统一对待这些文件夹和文件, 这种情形适合使用组合模式。
const Folder = function(folder) {
this.folder = folder
this.lists = []
}
Folder.prototype.add = function(res) {
this.lists.push(res)
}
Folder.prototype.scan = function() {
console.log(`开始扫描文件夹: ${this.folder}`)
for (let index = 0; index < this.lists.length; index++) {
this.lists[index].scan()
}
}
const File = function(file) {
this.file = file
}
File.prototype.add = function() {
throw Error('文件中不可添加文件')
}
File.prototype.scan = function() {
console.log(`开始扫描文件: ${this.file}`)
}
const folder = new Folder('根文件夹')
const folder1 = new Folder('JS')
const folder2 = new Folder('其他')
const file = new File('JS prototype')
const file1 = new File('CSS 编程艺术')
const file2 = new File('HTML 标记语言')
const file3 = new File('HTTP-TCP-IP')
folder.add(folder1)
folder.add(folder2)
folder1.add(file)
folder2.add(file1)
folder2.add(file2)
folder2.add(file3)
folder.scan()
// 开始扫描文件夹: 根文件夹
// 开始扫描文件夹: JS
// 开始扫描文件: JS prototype
// 开始扫描文件夹: 其他
// 开始扫描文件: CSS 编程艺术
// 开始扫描文件: HTML 标记语言
// 开始扫描文件: HTTP-TCP-IP
请关注我的订阅号,不定期推送有关 JS 的技术文章,只谈技术不谈八卦 😊
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。