0

次の設計上の問題があります
。2Resource種類のアクセサがあります。

  • 1つはそれを変更することです(それを呼びましょうAccess
  • 1つはconstのようなアクセス用です(これを呼びましょうConst_access)が、c1 = c2と言うと、c1がc2にアクセスします。

それが大きいことを考えるとResource、私は次のコピーメカニズムを達成する必要があります。

Access->Access:             deep copy
Access->Const_access:       deep copy
Const_access->Access:       deep copy
Const_access->Const_access: shallow copy

の関数を正確に使用できるように書くことを目指してAccessいます。私の現在の実装には欠陥があり、以下を使用しています。Const_accessconstAccess

class Access {
  public:
  Access(const Access&); // deep copy
  void method(const Access&); 
  void const_method() const; 
  protected: 
  Resource res;
};
class Const_access : public Access{
  private:
  void method(); // only declaration
  public:
  Const_access(const Const_accesss&); // shallow copy
  explicit Const_access(const Access&); // deep copy
};

しかし、ここでConst_access ca; ca.Access::method()はまだ機能し、非定数アクセサーを手動で隠す必要があります。保護された継承またはプライベート継承を試しましたが、それAccess&を処理するための柔軟性が妨げられていConst_Access&ます。

この問題の正しい解決策は何でしょうか?

4

3 に答える 3

2

あなたの言っていることは矛盾しています。

一方では、次のようなことを禁止したいと考えています。

Const_access foo;
foo.modify();

しかし一方で、次のようなことを許可したい:

void bar(Access& a) {
    a.modify();
}

Const_access foo;
bar(foo);

これは意味がありません。

より論理的な関係は、継承構造を変えることです。

class Const_access {
public:
    Const_access(const Const_access&); // shallow copy
    void const_method() const;
protected:
    Resource res; // or perhaps a reference-counted pointer?
};

class Access: public Const_access {
public:
    Access(const Access&); // deep copy
    explicit Access(const Const_access&); // deep copy
    void method();
};

それが与えない唯一のものは、 を に変換するときのディープコピーAccess ですConst_access

于 2012-11-12T12:40:41.207 に答える
0

関数method()は基本クラスで公開されていますが、派生クラスでは非公開です。これはリスコフの置換原理に違反しています。派生クラスは、基本クラスを縮小するのではなく、拡張する必要があります。

解決策は、その原則に違反しないことです。たとえば、class Const_accessプライベートまたはプロテクトで継承を行うか、で実装method()を提供しclass Const_accessます。

于 2012-11-12T12:39:07.290 に答える
0

この問題は、いわゆる遅延評価を使用して簡単に解決できます
。メンバー関数がそれを変更したい場合にのみ、クラス リソースのプライベート クローンを作成します。リソースへの R/W および読み取り専用アクセスは、プライベート継承で簡単に解決できます。

このようにして、LSP も遵守されます。必要に応じて、Objから完全にパブリックに継承されるようになりました。完全な回答へのリンクがあります。Const_obj

于 2012-11-14T17:54:39.707 に答える