我正在开发一个分区工具,我在设计中遇到了问题。我有一个类(称为CtrlFactories),它将读取MBR并为MBR中找到的每个分区构建一个对象。我为每种类型的分区都有一个类,每个分区都有一个Factory。
以下是它的样子:
(我在示例中只放了NTFS和FAT32,但每种类型的分区都有一个)。
我的想法是将IFactory放入类似的内容:
std::map< EPartType, IFactory* > mpFactories;
在构造函数或某些init函数中构建它:
IFactory::IFactory()
{
mpFactories[PART_NTFS] = new FactoryNTFS();
mpFactories[PART_FAT32] = new FactoryFAT32();
mpFactories[PART_EXT2] = new FactoryEXT2();
...
}
在“构建”功能中,执行:
int CtrlFactories::Build()
{
...
MBR mbr;
BuildMBR( mbr );
//... here I loop all the partitions found...
for( /*each partition*/ )
{
IPartition* part = mpFactories[ mbr.GetPartType() ]->Build( mbr.PartPosition() );
//..and store each partition somewhere
}
}
关键是:我有很多分区类型(> 100),在大多数情况下,用户在HD中只有两种或三种不同类型的分区。因此,分配所有工厂并且不使用大部分工厂似乎浪费时间和内存。我认为这里的懒惰初始化会好得多,但后来我需要一个像:
这样的代码 switch( mbr.GetPartType() )
{
case PART_NTFS:
if ( mpFactories[ PART_NTFS ] == NULL )
mpFactories[PART_NTFS] = new FactoryNTFS();
break;
case PART_FAT32:
if ( mpFactories[ PART_32 ] == NULL )
mpFactories[PART_32] = new Factory32();
break;
...
}
}
非常长的开关/案例会给代码增加太多的ciclomatic复杂性(即使代码很容易理解)。
那么,对于这个问题是否有更好的解决方案,可以避免很长的“切换/案例”并且不会浪费资源?
答案 0 :(得分:1)
一种方法是使用Singleton模式实现工厂。在每个工厂类上都有一个静态Instance()
方法来管理它的实例化。然后在地图中,您可以存储指向该方法的函数指针。
在您的Build()
代码中,您正在查找指向您遇到的每个分区的工厂的Instance()
方法的指针。使用该指针获取所需的实际工厂,然后从那里继续。