1

インターフェイスを使用して、非常にモジュール化されたプログラムを作成しようとしています。C# のバックグラウンドから来て、インターフェイスを変数の型として使用し、ポリモーフィズムを使用して、自分自身/他の人がこのインターフェイスから継承するさまざまなオブジェクトを関数/変数に渡すことができるようにしました。ただし、これを C++ で実行しようとすると、多くの奇妙なエラーが発生します。ここで何が間違っていますか?

インターフェイス型の変数を使用できるようにしたいと考えています。ただし、次の場合はコンパイル エラーが発生します。コンパイラは、抽象クラスなどから継承しているため、私の ErrorLogger クラスが抽象であると考えていると思います。

ILogger * errorLogger = ErrorLogger();

error C2440: 'initializing' : cannot convert from 'automation::ErrorLogger' to 'automation::ILogger *'

私がこれを間違った方法で行っている場合は、設計に関しても、私は学んでおり、あらゆるアドバイスに喜んで耳を傾けます.

ILogger.h:

#ifndef _ILOGGER_H_
#define _ILOGGER_H_

namespace automation
{
    class ILogger
    {
    public:
        virtual void Log(const IError &error) = 0;
    };
}
#endif

ErrorLogger.h:

#ifndef _ERRORLOGGER_H_
#define _ERRORLOGGER_H_
#include "ILogger.h"
#include "IError.h"

/* Writes unhandled errors to a memory-mapped file.
 * 
**/

namespace automation
{
    class ErrorLogger : public ILogger
    {
    public:
        ErrorLogger(const wchar_t * file = nullptr, const FILE * stream = nullptr);
        ~ErrorLogger(void);
        void Log(const IError &error);
    };
}
#endif

ErrorLogger.cpp:

#include "stdafx.h"
#include "ErrorLogger.h"
#include "IError.h"

using namespace automation;

ErrorLogger::ErrorLogger(const wchar_t * file, const FILE * stream)
{

}

void ErrorLogger::Log(const IError &error)
{
    wprintf_s(L"ILogger->ErrorLogger.Log()");
}

ErrorLogger::~ErrorLogger(void)
{
}

IError.h:

#ifndef _IERROR_H_
#define _IERROR_H_

namespace automation
{
    class IError
    {
    public:
        virtual const wchar_t *GetErrorMessage() = 0;
        virtual const int &GetLineNumber() = 0;
    };
}
#endif

コンパイル エラー:

ここに画像の説明を入力

ありがとう - フランシスコ

4

2 に答える 2

3

ILogger * errorLogger = ErrorLogger(); errorLoggerはポインタです。 で初期化する必要がありますnew operator

派生クラスを指す基本ポインターを定義する正しい方法は次のとおりです。

automation::ILogger * errorLogger = new automation::ErrorLogger();
//                                  ^^^^

最新の C++ ではスマート ポインターを使用することをお勧めします。

#include <memory>
std::unique_ptr<automation::ILogger> errorLoggerPtr(new automation::ErrorLogger());

IError.hまた、含める必要がありますILogger.h

#include "IError.h"

その他の提案:

1 FILEの代わりにfstreamを使用 2 wchar_tの代わりにstd::wstringを 使用* 2 cpp ファイルで、呼び出さない

using namespace automation;

代わりに、ヘッダー ファイルで行ったように、関数定義を名前空間でラップします。

namespace automation
{
    ErrorLogger::ErrorLogger(const std::wstring& file, std::ofstream& stream)
    {
    }
}

ポイントは、C++ コードと C コードを混在させないことです。文字列のような C++ クラス、fstream はRAIIを提供します。より安全で使いやすいです。

于 2013-07-12T23:34:27.830 に答える
0

ヘッダーファイル#include "IError.h"で必要です。ILogger.h

于 2013-07-12T23:09:26.160 に答える