0

問題

プロジェクトを Unicode でビルドしますが、ASCII でファイル (文字列と考える) を読み書きするには CMyDoc::Serialize() 関数が必要です。問題は、Unicode では、CArchive クラスが自動的に Unicode のすべての文字列を読み書きすることです。これは望ましくありません。

私の解決策

私の解決策は、ASCII文字列もサポートする独自のクラスCArchiveAを派生させることです。CArchiveこれが私のクラス定義です。

class CArchiveA : public CArchive
{

public:
    CArchiveA(CFile* pFile,
                UINT nMode,
                int nBufSize = 4096,
                void* lpBuf = NULL);

    CArchiveA( CArchive & ar );

    virtual ~CArchiveA();

    BOOL ReadStringA(CStringA& rString);
    LPSTR ReadStringA(_Out_z_cap_(nMax+1) LPSTR lpsz, _In_ UINT nMax);

    void WriteStringA(LPCSTR lpsz);


};

Serialize今、私はドキュメントのファイル機能でこのようなことをしたいと思っていました。

void CTestDoc::Serialize(CArchive& ar)
{
    CArchiveA & ar_a ( ar );

    // text is of type CStringA

    if (ar.IsStoring())
    {
        // TODO: add storing code here
        ar_a.WriteStringA( text );
    }
    else
    {
        // TODO: add loading code here

        ar_a.ReadStringA( text );
    }
}

しかし、上記の最初の行CArchiveA & ar_a ( ar );はコンパイラ エラーです。

質問

今日は錆びているだけかもしれませんがCArchive、自分の派生クラスに変換して操作できるようにするにはどうすればよいCArchiveAですか? CArchive最初のパラメーターとして受け入れCArchiveて ASCII 文字列を書き込むヘルパー関数から派生させずに作成したほうがよいでしょうか?

これは、特定のライブラリから基本クラスの機能を拡張する興味深いケース スタディだと思います。オブジェクト指向設計を探しながら、ソリューションのその側面も探求したいと思います。色々と考えはありますが、まずはお話をお聞きしたいです。その意味での質問は、(たとえば) ライブラリ クラスの機能が少し不足している場合に、このような問題を解決する最善の方法は何でしょうか? ありがとう。

4

1 に答える 1

1

この仕事では、封じ込めは継承よりも優れたツールだと思います。

CArchiveA公開継承により、それは is-aと言っていますCArchive

この関係は可換ではありません。親子関係に似ています。したがって、CArchiveオブジェクトはオブジェクトではなく、参照を使用してオブジェクトを指すCArchiveAことはできません。CArchiveACArchive

より良い選択は、CArchiveAクラスをオブジェクトのラッパーにして、CArchiveオブジェクトから継承するのではなく含めることです。CArchiveAオブジェクトまたは参照を受け取り、CArchiveそれへの参照を保持するためのコンストラクターを定義して、ReadString/WriteString必要なことを行うメソッドを定義できます。

何らかのCArchive抽象インターフェースを実装している場合は、そこから派生することもできCArchiveAます。しかし、そうでない場合は、おそらくこれに継承を使用したくないでしょう。

于 2012-05-24T16:00:53.990 に答える