2016-04-13 31 views
1

我有一些類別中大量的字符串分組,這些字符串分組在一個最終的巨人類中。這個類必須由另一個類和它不可改變的內容填充給某些客戶。 (當然,這些類是更復雜的,這是一個簡化的示意性表示。)具有不同訪問權限的類別:只讀許可權限,可寫入特權

解決方案1:

class A 
{ 
friend class M; 

private: 
    B m_b; 
    C m_c; 
    D m_d; 

public: 
    const B& GetB() const { return m_b;} 
    const C& GetC() const { return m_C;} 
    const D& GetD() const { return m_D;} 

private: 
    B& GetB() { return m_b;} 
    C& GetC() { return m_C;} 
    D& GetD() { return m_D;} 
} 

其中B是這樣的:

class B 
{ 
friend class M; 

private: 
    std::string m_camel; 
    std::string m_pink; 
    std::string m_vandergraaf; 

public: 
    const std::string& Camel() const { return m_camel;} 
    const std::string& PinkFloyd() const { return m_pink;} 
    const std::string& VanDerGraafGenerator() const { return m_vandergraaf;} 

private: 
    void SetCamel(const char* prog) { m_camel = prog;} 
    void SetPinkFloyd(const char* prog) { m_pink = prog;} 
    void SetVanDerGraafGenerator(const char* prog) { m_vandergraaf = prog;} 
} 

更好的解決方案,即爲protected避免friend是將寫訪問類暴露給M和基本的只讀對世界。

解決方案2:對於B

class A 
{ 
protected: 
    B m_b; 
    C m_c; 
    D m_d; 

public: 
    const B& GetB() const { return m_b;} 
    const C& GetC() const { return m_C;} 
    const D& GetD() const { return m_D;} 
} 

// only visible to M 
class A_Write: public A 
{ 
public: 
    B& GetB() { return m_b;} 
    C& GetC() { return m_C;} 
    D& GetD() { return m_D;} 
} 

同樣的事情,也許。這不是一個很好的解決方案,因爲客戶端也可以派生自己的類。

甲更好,但多個約束變體是溶液3:

class A 
{ 
private: 
    const B m_b; 
    const C m_c; 
    const D m_d; 

public: 
    const B& GetB() const { return m_b;} 
    const C& GetC() const { return m_C;} 
    const D& GetD() const { return m_D;} 

protected: 
    A(const B& b, const C& c, const D& d): m_b(), m_c(c), m_d(d) {} 
} 

// only visible to M 
class A_Write: public A 
{ 
public: 
    A_Write(const B& b, const C& c, const D& d): A(b, c, d) {} 
} 

我首選的方案是4,這是... 3但具有B,C,d爲簡單struct!而非class ES。所以M可以直接在B,C,D中做任何事情,然後構造一個A_Write。

有什麼更好的點子?

+0

這就是一個代理可用於,以減少界面的可視性。你有沒有嘗試過? – skypjack

+0

你的意思是PIMPL嗎?這一個:http://en.wikipedia.org/wiki/Proxy_pattern?你的意思是虛擬的嗎? 我的第一個想法是這對我的情況來說太重了。我現在必須睡覺,再見! – Liviu

+0

你能否在一個答案中表達你的想法?用一些類架構? – Liviu

回答

1

可能的方法可能是使用代理來減少類的接口。
M將實例化/接收S的實例(以便能夠使用其接口修改它),但它會將代理P返回給讀取器(不會管理修改它)。
它遵循一個小例子:

struct S { 
    void value(int v) noexcept { t = v; } 
    int value() const noexcept { return t; } 
private: 
    int t{0}; 
}; 

struct P { 
    P(S& s): b{s} { } 
    int value() const noexcept { return b.value(); } 
private: 
    S& b; 
}; 

int main() { 
    // the class: full interface 
    S s; 
    // the proxy: reduced interface 
    P p{s}; 
} 
+0

我喜歡你的解決方案,但我認爲P可以返回一個常量引用S(和其他),以避免爲所有成員編寫「代理」函數(值)。 – Liviu

+0

我的公司首選第二種解決方案,雖然你們將它們分開,但它們更好。 – Liviu