I intend to call a function whenever m_logger<<"hello"<<"world"
is called. m_logger is of type ofstream.
每当调用m_logger <<“hello”<<“world”时,我打算调用一个函数。 m_logger属于ofstream类型。
So i decide to overload << with following signature
所以我决定用以下签名重载<<
friend ofstream& operator<<(ofstream &stream,char *str);
However the vc compiler gives following error:
但是vc编译器会出现以下错误:
error C2666: 'operator <<' : 6 overloads have similar conversions
错误C2666:'operator <<':6次重载具有类似的转换
Is there anyother way to achieve this, my objective is to divert all the write operation to ofstream object to different function?
有没有其他方法可以实现这一点,我的目标是将所有写操作转移到ofstream对象到不同的功能?
Creating an object of my own calss works for me, however how can i make it work like normal ofstream object which typecasts all system defined types into strings or char*. i know one approach would be to overload the operator for each and every type but is there a cleaner approach
创建我自己的calss对象对我有用,但是我怎样才能使它像普通的ofstream对象一样工作,它将所有系统定义的类型转换为字符串或char *。我知道一种方法是为每种类型的操作员重载但是有一种更清洁的方法
5 个解决方案
#1
The problem is that ofstream
is already overloaded this way. If you make mlogger
of a new type holding an ofstream
, then you can do this:
问题是ofstream已经过载了这种方式。如果你制作一个持有ofstream的新类型的mlogger,那么你可以这样做:
class mlogger_t {
public:
ofstream stream;
...
}
mlogger_t& operator<<(mlogger_t& stream, const string& str) {
stream.stream << str;
...
}
//EDIT: here is how to make this work for other types too using templates:
template<typename T> mlogger_t& operator<<(mlogger_t& stream, T val) {
stream.stream << val;
}
...
mlogger_t mlogger;
mlogger << "foo";
Also, you should definitely use a const string&
(as I did in this example) rather than a C-style string. If you really need it to be C-style, at least use const char *
.
此外,你绝对应该使用const字符串&(就像我在这个例子中所做的那样)而不是C风格的字符串。如果你真的需要它是C风格,至少使用const char *。
#2
"overload" isn't "override". You can overload a function or operator for arguments of different types; you cannot override an existing function or operator with your own implementation (aside from overriding virtual functions, which is obviously very different). The only exceptions are operator new
and operator delete
, where it's possible to override built-in ones.
“过载”不是“覆盖”。您可以为不同类型的参数重载函数或运算符;你不能用你自己的实现覆盖现有的函数或操作符(除了覆盖虚函数,这显然是非常不同的)。唯一的例外是operator new和operator delete,它可以覆盖内置的。
#3
You could change the type of the m_logger object.
您可以更改m_logger对象的类型。
#4
Depending on why you want to overload operator<<, the correct solution is either
根据您想要重载运算符< <的原因,正确的解决方案是< p>
- to use another type than a descendant of ostream as target stream; in that case you have to write all operators << yourself, but you can get help from templates if you want to forward by default.
使用另一种类型而不是ostream的后代作为目标流;在这种情况下,您必须自己编写所有运算符,但如果您希望默认转发,则可以从模板获取帮助。
Like this:
template <typename T>
myStream& operator<<(myStream& s, T const& v)
{
s.getStream() << v;
}
and you'll see that manipulators don't match the template, so you'll also need something like:
你会看到操纵器与模板不匹配,所以你还需要这样的东西:
myStream& operator<<(myStream& fl, std::ostream& (*fn)(std::ostream&))
{
s.getStream() << fn;
}
- to write your own streambuf which delegates I/O to a std::filebuf (this is a little too complicated to give an example here, search the web -- filtering streambuf is a good keyword for that. If I remember correctly, boost has an helper library for that which may be useful. Note that in this case, you'll probably end up by using another type that an fstream, but which will descend from ostream.
编写自己的streambuf,它将I / O委托给std :: filebuf(这有点太复杂,不能在这里给出一个例子,搜索网页 - 过滤streambuf是一个很好的关键词。如果我没记错的话,提升已经一个可能有用的辅助库。请注意,在这种情况下,你最终可能会使用另一种类型的fstream,但它将从ostream下载。
#5
What you should do is make a class and then define operator<<
. An operator overload must contain at least one user-defined type. Similarly, you can't write a new operator+(int, int)
.
你应该做的是创建一个类,然后定义operator <<。运算符重载必须至少包含一个用户定义的类型。同样,您不能编写新的运算符+(int,int)。
#1
The problem is that ofstream
is already overloaded this way. If you make mlogger
of a new type holding an ofstream
, then you can do this:
问题是ofstream已经过载了这种方式。如果你制作一个持有ofstream的新类型的mlogger,那么你可以这样做:
class mlogger_t {
public:
ofstream stream;
...
}
mlogger_t& operator<<(mlogger_t& stream, const string& str) {
stream.stream << str;
...
}
//EDIT: here is how to make this work for other types too using templates:
template<typename T> mlogger_t& operator<<(mlogger_t& stream, T val) {
stream.stream << val;
}
...
mlogger_t mlogger;
mlogger << "foo";
Also, you should definitely use a const string&
(as I did in this example) rather than a C-style string. If you really need it to be C-style, at least use const char *
.
此外,你绝对应该使用const字符串&(就像我在这个例子中所做的那样)而不是C风格的字符串。如果你真的需要它是C风格,至少使用const char *。
#2
"overload" isn't "override". You can overload a function or operator for arguments of different types; you cannot override an existing function or operator with your own implementation (aside from overriding virtual functions, which is obviously very different). The only exceptions are operator new
and operator delete
, where it's possible to override built-in ones.
“过载”不是“覆盖”。您可以为不同类型的参数重载函数或运算符;你不能用你自己的实现覆盖现有的函数或操作符(除了覆盖虚函数,这显然是非常不同的)。唯一的例外是operator new和operator delete,它可以覆盖内置的。
#3
You could change the type of the m_logger object.
您可以更改m_logger对象的类型。
#4
Depending on why you want to overload operator<<, the correct solution is either
根据您想要重载运算符< <的原因,正确的解决方案是< p>
- to use another type than a descendant of ostream as target stream; in that case you have to write all operators << yourself, but you can get help from templates if you want to forward by default.
使用另一种类型而不是ostream的后代作为目标流;在这种情况下,您必须自己编写所有运算符,但如果您希望默认转发,则可以从模板获取帮助。
Like this:
template <typename T>
myStream& operator<<(myStream& s, T const& v)
{
s.getStream() << v;
}
and you'll see that manipulators don't match the template, so you'll also need something like:
你会看到操纵器与模板不匹配,所以你还需要这样的东西:
myStream& operator<<(myStream& fl, std::ostream& (*fn)(std::ostream&))
{
s.getStream() << fn;
}
- to write your own streambuf which delegates I/O to a std::filebuf (this is a little too complicated to give an example here, search the web -- filtering streambuf is a good keyword for that. If I remember correctly, boost has an helper library for that which may be useful. Note that in this case, you'll probably end up by using another type that an fstream, but which will descend from ostream.
编写自己的streambuf,它将I / O委托给std :: filebuf(这有点太复杂,不能在这里给出一个例子,搜索网页 - 过滤streambuf是一个很好的关键词。如果我没记错的话,提升已经一个可能有用的辅助库。请注意,在这种情况下,你最终可能会使用另一种类型的fstream,但它将从ostream下载。
#5
What you should do is make a class and then define operator<<
. An operator overload must contain at least one user-defined type. Similarly, you can't write a new operator+(int, int)
.
你应该做的是创建一个类,然后定义operator <<。运算符重载必须至少包含一个用户定义的类型。同样,您不能编写新的运算符+(int,int)。