2011-12-02 3 views
2
그래서 같이, 서로에 대한 포인터를 보유 세 개의 클래스, config, circuitconn,이

:C++ 클래스

struct config { /* ... */ }; 
struct circuit { 
    config *cfg; 
    /* ... */ 
}; 
struct conn { 
    config *cfg; 
    circuit *ckt; 
    /* ... */ 
} 

(가를 액세스 제어 및이 프로그램에 대한 중간 ++ C로 C로 변환되고 통해 있기 때문에 어떤 포인터 정보는. 그것은 지금 중요하지 않습니다.) 이러한 클래스는 서브 클래스된다

, 모두 세 그룹의 서브 클래스 항상 입니다 :

struct foo_config : config { /* ... */ }; 
struct foo_circuit : circuit { /* ... */ }; 
struct foo_conn : conn { /* ... */ }; 

또한, 불변 런타임는 그 인스턴스에 foo_circuit 또는 foo_connfoo_config 인스턴스 항상 포인트 및 foo_conn에서 ckt 포인터 것 항상 점에서 cfg 포인터 foo_circuit입니다. 이것은 현재 dynamic_cast 및 단정으로 시행되고 있습니다. 현재 두 개의 다른 foo이 있지만 앞으로 더 많은 것이있을 수 있습니다.

cfgckt 포인터는 일반 circuitconn 클래스의 메소드에 접근을 유지하며,이 제네릭 형식을 가지고 있지만, 서브 클래스의 방법에서, 그 포인터가 적절한 서브 클래스 유형을 가질 수 있도록하는 것이 가능 사항을 마련하는 것입니다 , 위의 불변량은 컴파일 타임 적용이됩니까? 그렇다면 어떻게? 그렇지 않다면, 내가 대신 제안하는 바는 무엇입니까?

각 서브 클래스 집합에 대해 작성해야하는 상용구의 양을 최소화하는 대답을 선호합니다. 익명의 네임 스페이스에 하위 클래스가 정의되어 있고 머리글에 표시되지 않는 경우에도 여전히 작동하는 대답을 선호합니다.

답변

0

데이터 멤버에 대한 모든 직접 액세스를 getter 및 setter로 바꾸면 각 하위 클래스에 대해 유형별 getter 및 setter를 정의 할 수 있으며 컴파일러에서 유형을 적용 할 수있는 유형별 getter 및 setter를 정의 할 수 있습니다. 아래는 예제입니다. 서브 클래스 생성을 단순화하기 위해 템플릿 클래스를 정의했습니다.

struct config { /* ... */ }; 

struct circuit { 
private: 
    config *cfg; 
protected: 
    void set_cfg(config* _cfg) { cfg = _cfg; } 
    config* get_cfg() { return cfg; } 
}; 

template <typename CFG> 
struct my_circuit : circuit { 
public: 
    // type specific setters/getters 
    void set_cfg(CFG* _cfg) { circuit::set_cfg(_cfg); } 
    CFG* get_cfg() { return dynamic_cast<CFG*>(circuit::get_cfg()); } 
}; 

// below is how you define two different sets of subclasses: 
struct foo_config : config { /* ... */ }; 
typedef my_circuit<foo_config> foo_circuit; 

struct bar_config : config { /* ... */ }; 
typedef my_circuit<bar_config> bar_circuit; 

// example usage 
foo_config foo_cfg; 
foo_circuit foo_ckt; 
bar_config bar_cfg; 

foo_ckt.set_cfg(&foo_cfg); // okay 
foo_ckt.set_cfg(&bar_cfg); // not okay, compiler error! 

기본 클래스 안에는 아무 것도 변경할 필요가 없습니다. 서브 클래스 내부에서 이러한 멤버 변수에 대한 직접 액세스를 해당 getter로 바꿔야하므로 적절한 유형 변환을 얻을 수 있습니다. 기본 클래스의 데이터 멤버를 private로 변환하여 하위 클래스의 이러한 데이터 멤버에 대한 모든 직접적인 참조를 검색하는 컴파일러의 도움을 얻었습니다.