2012-03-06 2 views
0

C++ 프로젝트에서 "디자인"문제가 발생했습니다.팩토리에서 클래스 인스턴스를 관리하는 더 좋은 방법은 무엇입니까?

는 I는 클래스라는 한 Currency ("USD", "EUR" 수, 등등 ..., 그리고 몇 가지 방법을 가지고 할 수있는) 이 프로젝트의 모든 곳이 클래스의 새로운 에디션의 많은 경우가 있지만이 수 다른 통화 (~ 100)의 무리 일 수 있습니다.

그래서 나는 Currency가 물었다 이번이 처음을 할당하는 방법을 쓰고, 그렇지 않으면 기존 Currency를 반환

class Currency 
    { 
    public: 
     typedef std::map<std::string, Currency*> CurrencyMap_t; 
    public: 
     static CurrencyMap_t _currencies; 

    public: 
     static const Currency& getCcy(const std::string& name) 
     { 
     CurrencyMap_t::const_iterator it(_currencies.find(name)); 

     if (it == _currencies.end()) 
      it = _currencies.insert(std::make_pair(name, new Currency(name))).first; 

     return *(it->second); 
     } 

    private: 
     // can't instantiate from outside 
     Currency(); 
     Currency(const Currency& other); 
    private: 
     // private ctor 
     explicit Currency(const std::string& name) {... } 
    }; 

그래서 지금, 나는 각 다른 Currency의 한 인스턴스가 있습니다.

하지만, 기본 - 생성자가 정의되어 있지 않기 때문에 나는 더 이상하는 Currency 멤버를 들고 클래스를 가질 수 없습니다 :

class CcyPair 
    { 
    public: 
     CcyPair(const Currency& ccy1, const Currency& ccy2) {} 
    private: 
     Currency _ccy1; // won't compile because "no default-constructor available" 
     Currency _ccy2; 
    }; 

내가 CcyPair 클래스 Currency 포인터를 유지하고 싶지 않아요.

당신이 (여기 Currency 클래스) 클래스의 두 인스턴스가 같은 속성을 가지고 있다면, 그것은 같은 인스턴스가 실제로 있다는 보장 등 "패턴"을 구현하는 더 좋은 방법이 있나요 (동일한 기본 참조)?

+1

* 어떤 이유로 든 실제로 '통화'가 '통화'입니까? 그것은 큰 계급처럼 보이지 않으며, 그것으로 '새로운'이유가 없습니다. – Xeo

+0

'Currency' 클래스에는 public 생성자가 없기 때문에'Currency' 객체를 포함하는지도를 만들면 insert() –

+0

중에 복사 생성자를 호출 할 수 없습니다. 사실, @ kennbrodhagen의 해결책 나를 위해 일하는), 유일한 나머지 문제는 프로그램의 끝에 '통화'개체의 자동 삭제입니다. 내가 지적했듯이, 나는 단지'Currency' 객체를 보유 할 수없고, 나는 그것들을 new()해야한다. 그리고 나는 모든 인터페이스 등으로 외부 Flyweight Factory를 만들고 싶지 않다. 그래서 나는'std :: map >' –

답변

1

통화 개체에 대한 포인터를 보유하고 싶지 않지만 대신 참조를 보유하는 것에 대해 어떻게 생각하십니까? 나는 당신이 포인터를 피하고 싶었는지 확신 할 수 없기 때문에 NULL에 대한 많은 검사에 의해 부담을 느끼지 않거나 또 다른 이유가 있다면. 다음은 참조를 사용하는 CcyPair의 예입니다.

class CcyPair 
     { 
     public: 
     CcyPair(const Currency& ccy1, const Currency& ccy2) 
      : _ccy1(ccy1), _ccy2(ccy2) {} 

     CcyPair(const std::string& ccyName1, const std::string& ccyName2) 
      : _ccy1(Currency::getCcy(ccyName1)), _ccy2(Currency::getCcy(ccyName2)) {} 

     private: 
     // need to make these const since getCcy returns const 
     // you could also change the signature of getCcy to return non-const 
     const Currency & _ccy1; 
     const Currency & _ccy2; 
     }; 
+0

네, 맞습니다. 더 나은 "대안" –

+0

(정적 std :: map에서 boost :: shared_ptr <>을 사용하여 객체를 자동으로 삭제) –

3

당신이 찾고있는 것은 플라이급 패턴입니다. 읽기 http://en.wikipedia.org/wiki/Flyweight_pattern

BTW 플라이급과 관련이있을 수도 있지만 그 상태를 별도의 클래스로 필터링해야합니다.

+0

으로 갈 것입니다. 실제로 플라이급 패턴은 제 예제에서 구현 한 것보다 비슷합니다. –

관련 문제