2016-06-17 4 views
3

У меня есть класс с именем «Абонент», который наследуется от класса с именем «Клиент», который содержит следующие строки кода, в «защищенный»:Как правильно использовать использование в std: ostream & member, а «this» - const?

std::ostream& messagesSink; 

std::ostream& getMessagesSink() { 
    return messagesSink; 
} 

(messagesSink инициализируется в конструкторе абонентов)

и существует следующая функция-член в «абонента»:

virtual void recieveMessage(const std::string& message , 
     const Topic& topic, 
     const Client& client) const { 
    messagesSink << "Topic: "<< topic 
      << ". Sender: #" << client.getId() << ". Reciver: #" 
      << getId() << ".Message: " << message; 
} 

проблема выглядит следующим образом: в его текущем состоянии, код не содержит ошибок компиляции, но если я заменить использование messagesSink члена в функции getMessagesSink(), так как код ниже, появляется ошибка компиляции:

virtual void recieveMessage(const std::string& message , 
     const Topic& topic, 
     const Client& client) const { 
    getMessagesSink() << "Topic: "<< topic 
      << ". Sender: #" << client.getId() << ". Reciver: #" 
      << getId() << ".Message: " << message; 
} 

мои вопросы:

1), что является разностное между до и после?

2) как правильно использовать refrence для std :: ostream, а в функции, которая сохраняет это «как const»?

ответ

1

Проблема в том, что getMessagesSink не обозначен const. receiveMessage помечен const, поэтому он не может вызывать функции не-const-члена.

+0

Я попытался изменить возвращаемое значение getMessagesSink на «const std :: ostream &», но это просто приводит к ошибкам усложнения неверного преобразования из «const char *» в int, long int, long long int и так далее вперед, и я не понимаю, что ... зачем компилятор ожидает переменную типа «int»? есть способ передать объект типа ostream через функцию? –

+0

ой, и спасибо за ответ! –

+0

Это хорошо объясняет проблему, но не позволяет предложить решение. –

0

Вы не можете использовать функции не-const-члена внутри функций-членов const одного и того же объекта. Что касается компилятора, вы можете изменить объект, когда вы вызываете getMessagesSink().

Я думаю, что getMessagesSink() должен быть const, если вы не можете изменить это, и вы все еще хотите, чтобы ваша функция была const, вы можете сделать что-то подобное внутри receiveMessage().

Subscriber* self = const_cast<Subscriber*>(this); 
std::ostream& messageSink = self->getMessagesSink(); 

В противном случае вы должны либо сделать свою функцию неконстантной, либо просто использовать защищенный объект messagesSink напрямую. Конечно, если реализация getMessageSink() изменится, сделав что-то в std :: ostream, прежде чем возвращать ссылку на нее, ваш код, скорее всего, сломается или, по крайней мере, перестанет работать по назначению.

+0

Мех. 'const_cast' выглядит странно, и на самом деле он не нужен. Это то, что «изменяет» для членов класса. –