1、意图
定义一个用于创建对象的接口,让子类决定实例化哪一个类。Factory Method使一个类的实例化延迟到其子类。
2、适用性
在下列情况下可以使用Factory Method模式:
1)当一个类不知道它所必须创建的对象的类的时候。
2)当一个类希望由它的子类来指定它所创建的对象的时候。
定义一个用于创建对象的接口,让子类决定实例化哪一个类。Factory Method使一个类的实例化延迟到其子类。
2、适用性
在下列情况下可以使用Factory Method模式:
1)当一个类不知道它所必须创建的对象的类的时候。
2)当一个类希望由它的子类来指定它所创建的对象的时候。
3)当类将创建对象的职责委托给多个帮助子类中的某一个,并且你希望将哪一个帮助子类是代理者这一信息局部化的时候。
3、C++实例
// Test.cpp : 定义控制台应用程序的入口点。
//
#include "stdafx.h"
#include <iostream>
#include <Windows.h>
#include <list>
#include <string>
using namespace std;
enum Direction
{
North = 0,
South,
East,
West
};
class MapSite
{
public:
virtual void Enter()=0;
};
class Room: public MapSite
{
public:
Room( int roomNo )
{
_roomNumber = roomNo;
}
MapSite* GetSide( Direction d ) const
{
return _sides[d];
}
void SetSide( Direction d, MapSite *m )
{
_sides[d] = m;
}
virtual void Enter()
{
}
private:
MapSite *_sides[4];
int _roomNumber;
};
class RoomWithABomb:public Room
{
public:
RoomWithABomb( int roomNo ): Room( roomNo )
{
_roomNumber = roomNo;
}
MapSite* GetSide( Direction d ) const
{
return _sides[d];
}
void SetSide( Direction d, MapSite *m )
{
_sides[d] = m;
}
virtual void Enter()
{
}
// ......Bomb
private:
MapSite *_sides[4];
int _roomNumber;
// Bomb
};
class Wall: public MapSite
{
public:
Wall()
{
}
virtual void Enter()
{
}
};
class BombedWall: public Wall
{
public:
BombedWall()
{
}
virtual void Enter()
{
}
// ......Bomb
};
class Door:public MapSite
{
public:
Door( Room* r1 = NULL, Room* r2 = NULL )
{
_room1 = r1;
_room2 = r2;
}
virtual void Enter()
{
}
Room* OtherSideFrom( Room *r )
{
return NULL;
}
private:
Room* _room1;
Room* _room2;
bool _isOpen;
};
class Maze
{
public:
Maze()
{
}
void AddRoom( Room *r )
{
_room = r;
}
Room* RoomNo( int no ) const
{
return new Room( no );
}
private:
Room *_room;
};
class MazeGame
{
public:
MazeGame( )
{
}
virtual Maze* MakeMaze( ) const
{
return new Maze;
}
virtual Room* MakeRoom( int n ) const
{
return new Room( n );
}
virtual Wall* MakeWall( ) const
{
return new Wall;
}
virtual Door* MakeDoor( Room *r1, Room *r2 ) const
{
return new Door( r1, r2 );
}
Maze* CreateMaze( )
{
Maze* aMaze = MakeMaze();
Room *r1 = MakeRoom( 1 );
Room *r2 = MakeRoom( 2 );
Door *theDoor = MakeDoor( r1, r2 );
aMaze->AddRoom( r1 );
aMaze->AddRoom( r2 );
r1->SetSide( North, MakeWall() );
r1->SetSide( East, theDoor );
r1->SetSide( South, MakeWall() );
r1->SetSide( West, MakeWall() );
r2->SetSide( North, MakeWall() );
r2->SetSide( East, MakeWall() );
r2->SetSide( South, MakeWall() );
r2->SetSide( West, theDoor );
return aMaze;
}
};
class BombedMazeGame: public MazeGame
{
public:
BombedMazeGame()
{
}
virtual Wall* MakeWall( ) const
{
return new BombedWall;
}
virtual Room* MakeRoom( int n ) const
{
return new RoomWithABomb( n );
}
};
class EnchantedMazeGame: public MazeGame
{
public:
EnchantedMazeGame()
{
}
virtual Wall* MakeWall( ) const
{
return MazeGame::MakeWall();
}
virtual Room* MakeRoom( int n ) const
{
return MazeGame::MakeRoom( n );
}
};
int _tmain(int argc, _TCHAR* argv[])
{
BombedMazeGame *bomgame = new BombedMazeGame;
EnchantedMazeGame *engame = new EnchantedMazeGame;
Maze* bommaze = bomgame->CreateMaze();
Maze* enmaze = engame->CreateMaze();
delete enmaze;
delete bommaze;
delete bomgame;
delete engame;
return 0;
}