Как перегрузить оператор ostream <<, чтобы он работал с log4cxx в C++?
Скажем, у меня есть класс A и оператор<<, объявленный так:
// A.h
class A
{
// A stuff
};
std::ostream& operator<<(std::ostream& os, const A& a);
где-то еще я использую свой логгер с A:
LoggerPtr logger(LogManager::getLogger("ThisObject"));
A a;
LOG4CXX_INFO(logger, "A: " << a);
Компилятор жалуется: двоичный файл "<<": не найден оператор, который принимает правый операнд типа "const A" (или нет приемлемого преобразования) D: \ dev \ cpp \ lib \ apache-log4cxx \ log4cxx \ include \ log4cxx \ helpers \ messagebuffer.h 190
Эта ошибка приводит меня к объявлению operator<<
:
// messagebuffer.h
template<class V>
std::basic_ostream<char>& operator<<(CharMessageBuffer& os, const V& val) {
return ((std::basic_ostream<char>&) os) << val;
}
LOG4XX_INFO
макрос расширяется до:
#define LOG4CXX_INFO(logger, message) { \
if (logger->isInfoEnabled()) {\
::log4cxx::helpers::MessageBuffer oss_; \
logger->forcedLog(::log4cxx::Level::getInfo(), oss_.str(oss_ << message), LOG4CXX_LOCATION); }}
MessageBuffer
"определяет" и этот оператор:
// messagebuffer.h
template<class V>
std::ostream& operator<<(MessageBuffer& os, const V& val) {
return ((std::ostream&) os) << val;
}
Я не понимаю, как правильно перегрузить этот оператор, чтобы он работал. Любая идея?
3 ответа
Вы можете попытаться объявить свой оператор << в пространстве имен std (это допустимо, поскольку вы передаете экземпляр вашего пользовательского типа):
namespace std {
ostream& operator<<(ostream& os, const A& a);
}
Предложение Алана поставить пользовательский оператор в std
пространство имен работает. Но я предпочитаю помещать пользовательский оператор в log4cxx::helpers
пространство имен, которое тоже работает. В частности,
namespace log4cxx { namespace helpers {
ostream& operator<<(ostream& os, const A& a);
} }
Сейчас у меня нет доступного компилятора, но я думаю, что проблема вызвана попыткой использовать оператор вставки в константную строку. "A: " << a