23种设计模式(C++)之 组合(Composite)模式

23种设计模式(C++)之 组合(Composite)模式

23种设计模式(C++)之 组合(Composite)模式

意图

将对象组合成树形结构以表示“部分-整体”的层次结构。Composite使得用户对单个对象和组合对象的使用具有一致性。

场景

比如文件存储系统,文件系统可分为两种组件:文件组件和文件夹组件,这两种组件却可以组合出非常庞大复杂的文件系统。
再比如树,树可以分为树干组件和树叶组件,这两种组件却可以组合出参天大树。

角色

  • Composite
    • 为组合中的对象声明接口。
    • 在适当的情况下,实现所有类共有接口的缺省行为。
    • 声明一个接口用于访问和管理Component的子组件。
    • (可选)在递归结构中定义一个接口,用于访问一个父部件,并在合适的情况下实现它。
  • Leaf
    • 在组合中表示叶节点对象,叶节点没有子节点。
    • 在组合中定义图元对象的行为。
  • Composite
    • 定义有子部件的那些部件的行为。
    • 存储子部件。
    • 在Component接口中实现与子部件有关的操作。
  • Client
    • 通过Component接口操纵组合部件的对象。

实例

以树为例,树包含树干和叶子两个组件。

  1. 定义组件接口
    同时提供访问和管理组件的方法。
class Root
{
private:
	string name;
public:
	Root(string name)
	{
		this->name = name;
	}
	string getName()
	{
		return this->name;
	}
	virtual void add(Root* root) = 0;
	virtual void remove(Root* root) = 0;
	virtual void printNodes() = 0;
};
  1. 定义叶子组件
    注:该组件没有子组件。
class Leaf : public Root
{
private:
	vector<Root*> rootVector;
public:
	Leaf(string name) : Root(name)
	{

	}
	void add(Root* root)
	{
		cout << "Can not add object to Leaf" << endl;
	}
	void remove(Root* root)
	{
		cout << "Can not remove object to Leaf" << endl;
	}
	void printNodes()
	{
		cout << this->getName() << endl;
	}
};
  1. 定义组合组件
class Branch : public Root
{
private:
	vector<Root*> rootVector;
public:
	Branch(string name): Root(name)
	{
		
	}
	void add(Root* root)
	{
		rootVector.push_back(root);
	}
	void remove(Root* root)
	{
		vector<Root*>::iterator it;
		for (it = rootVector.begin(); it != rootVector.end();)
		{
			if (*it == root)
			{
				cout << (*it)->getName() << " is erased." << endl;
				it = rootVector.erase(it);
			}
			else
			{
				it++;
			}
		}
	}
	void printNodes()
	{
		vector<Root*>::iterator it;
		for (it = rootVector.begin(); it != rootVector.end();it++)
		{
			cout << (*it)->getName() << endl;
		}
	}
};

  1. Client测试
int main()
{
	Root* root = new Branch("myWorkspace");
	cout << "************** Add leaf1 and leaf2 ***************" << endl;
	Root* leaf1 = new Leaf("leaf1");
	root->add(leaf1);
	root->add(new Leaf("leaf2"));
	root->printNodes();
	cout << "************** Add branch1 ***************" << endl;
	Root* branch1 = new Branch("branch1");
	branch1->add(new Leaf("leaf3"));
	root->add(branch1);
	root->printNodes();
	cout << "************** Add branch2 ***************" << endl;
	Root* branch2 = new Branch("branch2");
	branch2->add(branch1);
	root->add(branch2);
	root->printNodes();
	cout << "************** Remove leaf1 ***************" << endl;
	root->remove(leaf1);
	root->printNodes();
	cout << "************** Remove branch2 ***************" << endl;
	root->remove(branch2);
	root->printNodes();
}
  1. 结果
************** Add leaf1 and leaf2 ***************
leaf1
leaf2
************** Add branch1 ***************
leaf1
leaf2
branch1
************** Add branch2 ***************
leaf1
leaf2
branch1
branch2
************** Remove leaf1 ***************
leaf1 is erased.
leaf2
branch1
branch2
************** Remove branch2 ***************
branch2 is erased.
leaf2
branch1
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值