资源描述
Flyweight模式
一.意图运用共享技术有效地支持大量细粒度的对象。
二.适用性1、一个应用程序使用了大量的对象。2、完全由于使用大量的对象,造成特别大的存储开销。3、对象的大多数状态都可变为外部状态。4、要是删除对象的外部状态,那么能够用相对较少的共享对象取代许多组对象。5、应用程序不依靠于对象标识。由于Flyweight对象能够被共享,关于概念上明显有不的对象,标识测试将返回真值。
三.实例:
设计一个图书的治理系统,每本书都有出版社、编号、作者、价钞票等的属性,因此那个书的类能够如此设计:
classBook
{
public:
stringGetPublish(){returnm_publishCompany;}
stringGetWriter(){returnm_writer;}
intGetBookID(){returnm_bookID;}
intGetPrice(){returnm_price;}
stringGetName(){returnm_name;}
voidSetPublish(string&s){m_publishCompany=s;}
voidSetWriter(string&s){m_writer=s;}
voidSetBookID(intid){m_bookID=id;}
voidSetPrice(intprice){m_price=price;}
voidSetName(string&s){m_name=s;}
private:
stringm_publishCompany;//出版社
stringm_writer;//作者
intm_bookID;//书籍编号
intm_price;//价钞票
stringm_name;//书名
};
这特不自然。然而随着系统的开发和试运行,这种设计就表现出一些缺乏的地点了,例如一般图书会特不多,成千上万本,在这些书中可能会有相同的出版社或者相同的作者,那对每本书来讲就会重复了,也确实是根基白费了一些重复的空间。
要是每本书都消耗一些空间,那整个软件系统所消耗的空间是不可想象的。因此,我们就要想方法来解决那个咨询题。
想象一下系统里面Book类的使用:
1、先瞧瞧不用共享模式:
Bookbook1,book2,book3;
book1.SetPublish("机械工业出版社");
book1.SetWriter("候捷");
book1.SetBookID(0000);
book1.SetPrice(20);
book1.SetName("C++好野");
book2.SetPublish("人民邮电出版社");
book2.SetWriter("候捷");
book2.SetBookID(0001);
tPrice(30);
book2.SetName("C++是好劲");
book3.SetPublish("机械工业出版社");
book3.SetWriter("一雨田");
book3.SetBookID(0002);
book3.SetPrice(50);
book3.SetName("C++无得顶,我是铁头功...");
那个地点有两个“机械工业出版社〞和两个“候捷〞,重复了。要是使用共享模式的话,那个地点的白费就能够防止了。
不瞧那个地点只有两个,想象一下成千上万本书时的空间白费...
2、使用共享模式,把出版社和作者两个属性作为享元(Fly~~Weight)
PublishFlyweightFactorypff;
WriterFlyweightFactorywff;
Bookbook1,book2,book3;
book1.SetPublish(pff.GetPublish("机械工业出版社")->GetName());
ter(wff.GetWriter("候捷")->GetName());
book1.SetBookID(0000);
book1.SetPrice(20);
book1.SetName("C++好野");
book2.SetPublish(pff.GetPublish("人民邮电出版社")->GetName());
book2.SetWriter(wff.GetWriter("候捷")->GetName());
book2.SetBookID(0001);
book2.SetPrice(30);
book2.SetName("C++是好劲");
blish("机械工业出版社")->GetName());
book3.SetWriter(wff.GetWriter("一雨田")->GetName());
book3.SetBookID(0002);
book3.SetPrice(50);
book3.SetName("C++无得顶,我是铁头功...");
什么缘故使用了PublishFlyweightFactory和WriterFlyweightFactory之后就能够节约空间了呢?微妙就在于GetPublish和GetWriter的实现:
PublishFlyweight*GetPublish(stringkey)
{
PublishFlyweight*p;
mapPublish::iteratorit;
it=mapPublish.find(key);
//存在那个Writer
if(it!=mapPublish.end())
p=it;
else
{//插进那个PublishFlyweight
p=newPublishFlyweight(key);
mapPublish[key]=p;
}
returnp;
}
GetWriter的实现大同小异,那个地点就不列出来了,请瞧具体代码里的实现。
下面是完整的代码,能够在一个CPP文件里编译使用:
#pragmawarning(disable:4786)
#include<iostream>
#include<map>
#include<string>
usingnamespacestd;
classBook
{
public:
stringGetPublish(){return*m_publishCompany;}
stringGetWriter(){return*m_writer;}
intGetBookID(){returnm_bookID;}
intGetPrice(){returnm_price;}
stringGetName(){returnm_name;}
voidSetPublish(string*s){m_publishCompany=s;}
voidSetWriter(string*s){m_writer=s;}
voidSetBookID(intid){m_bookID=id;}
voidSetPrice(intprice){m_price=price;}
voidSetName(string&s){m_name=s;}
private:
string*m_publishCompany;//出版社
string*m_writer;//作者
intm_bookID;//书籍编号
intm_price;//价钞票
stringm_name;//书名
};
classPublishFlyweight
{
public:
PublishFlyweight(strings)
{m_name=s;}
stringGetName()
{returnm_name;}
private:
stringm_name;
};
classPublishFlyweightFactory
{
public:
PublishFlyweight*GetPublish(stringkey)
{
PublishFlyweight*p;
map<string,PublishFlyweight*>::iteratorit;
it=mapPublish.find(key);
//存在那个出版社
if(it!=mapPublish.end())
{
p=(*it).second;
cout<<"差不多有那个出版社:"<<p->GetName()<<"你节约了"<<strlen(p->GetName().c_str())<<"字节的空间"<<endl;
}
else
{//插进那个PublishFlyweight
p=newPublishFlyweight(key);
mapPublish[key]=p;
}
returnp;
}
private:
map<string,PublishFlyweight*>mapPublish;
};
classWriterFlyweight
{
public:
WriterFlyweight(strings)
{
m_name=s;
}
stringGetName()
{
returnm_name;
}
private:
stringm_name;
};
classWriterFlyweightFactory
{
public:
WriterFlyweight*GetWriter(stringkey)
{
WriterFlyweight*p;
map<string,WriterFlyweight*>::iteratorit;
it=mapWriter.find(key);
//存在那个Writer
if(it!=mapWriter.end())
{
p=(*it).second;
cout<<"差不多有那个作者名字:"<<p->GetName()<<"你节约了"<<strlen(p->GetName().c_str())<<"字节的空间"<<endl;
}
else
{//插进那个PublishFlyweight
p=newWriterFlyweight(key);
mapWriter[key]=p;
}
returnp;
}
private:
map<string,WriterFlyweight*>mapWriter;
};
voidShowBookInfo(Bookbook)
{
cout<<"书名:Name()<<endl;
cout<<"编号:"<<book.GetBookID()<<endl;
cout<<"价钞票:"<<book.GetPrice()<<endl;
cout<<"出版:"<<book.GetPublish()<<endl;
cout<<""<<book.GetWriter()<<endl;
cout<<endl;
}
voidmain()
{
PublishFlyweightFactorypff;
WriterFlyweightFactorywff;
Bookbook1,book2,book3;
book1.SetPublish(&(pff.GetPublish("机械工业出版社")->GetName()));
book1.SetWriter(&(wff.GetWriter("候捷")->GetName()));
book1.SetBookID(0000);
book1.SetPrice(20);
book1.SetName(string("<<C++好野>>"));
ShowBookInfo(book1);
sh("人民邮电出版社")->GetName()));
book2.SetWriter(&(wff.GetWriter("候捷")->GetName()));
book2.SetBookID(0001);
book2.SetPrice(30);
book2.SetName(string("<<C++是好劲>>"));
ShowBookInfo(book2);
booketPublish(&(pff.GetPublish("机械工业出版社")->GetName()));
book3.SetWriter(&(wff.GetWriter("一雨田")->GetName()));
book3.SetBookID(0002);
book3.SetPrice(50);
book3.SetName(string("<<C++无得顶,我是铁头功...>>"));
ShowBookInfo(book3);
}
展开阅读全文