Конструктор класса & quot; C2248: ‘std :: basic_ios & lt; _Elem, _Traits & gt; :: basic_ios’: не может получить доступ к закрытому члену, объявленному в классе ‘std :: basic_ios & lt; _Elem, _Traits & gt; & quot;

Это мой первый пост.

Я прочитал много тем и, кажется, все сделал правильно, но я снова получаю сообщение об ошибке выше, когда пытаюсь скомпилировать следующий код:

// Header file

#include <fstream>
#include <ostream>
#include <string>

using namespace std;

class CLogger
{
private:
ostream m_oStream;

public:
CLogger(ostream& oStream);
CLogger(const string sFileName);
};

// Implementation file

CLogger::CLogger(ostream& oStream) :
m_oStream(oStream) // <-- Here is the problem?!
{
}

CLogger::CLogger(const string sFileName) :
m_oStream(ofstream(sFileName.c_str()))
{
}

Не могли бы вы помочь мне?

Большое спасибо!

2

Решение

CLogger::CLogger(ostream& oStream) : // <-- Here is the problem?!
m_oStream(oStream)

Проблема не в первой строке, а во второй.

С членом m_oStream объявляется не ссылочным, вторая строка выше пытается сделать копию oStream что невозможно, потому что экземпляр-конструктор std::ostream отключен, сделав это private, что вы видите в сообщении об ошибке «не может получить доступ к приватному члену.»

Исправление таково:

std::ostream * m_oStream; //declare it as pointer.
bool m_deleteStream;      //flag whether to delete m_oStream or not

Теперь сделайте это:

CLogger::CLogger(ostream& oStream) :
m_oStream(&oStream), m_deleteStream(false)
{
}

CLogger::CLogger(const string sFileName) :
m_oStream(new std::ofstream(sFileName)), m_deleteStream(true)
{
//Note : in C++03, you've to pass sFileName.c_str() to
//the constructor of std::ostream
}

и тогда вы должны написать деструктор как:

~CLogger()
{
if ( m_deleteStream )
{
delete m_oStream;
}
}

Важный момент: поскольку это класс управления ресурсами (logger), было бы неплохо сделать его недоступным для копирования, поскольку копирование не имеет смысла для экземпляров logger.

6

Другие решения

В

m_oStream(ofstream(sFileName.c_str()))

вы строите ofstream и скопировать-построить свой m_oStream с этим. Просто пиши

m_oStream(sFileName.c_str())

Потоки не являются ни копируемыми, ни копируемыми, хотя они являются подвижными типами, так что я думаю, что вы не используя C ++ 11 в этом примере.

По той же причине,

CLogger::CLogger(ostream& oStream) :
m_oStream(oStream)

не собирается работать. Вы не можете делать копии, вы можете только перемещать (в C ++ 11) или содержать ссылку какой-либо формы.


Примечание:

Из вашего примера не совсем понятно, сделали ли вы это, но не забудьте включить охрану в свой заголовочный файл.

0

По вопросам рекламы [email protected]