I want to overload the "receiver" operator so I can do this: someClass >> myClass.
...where myClass is the class which I need to overload the operator for.
Hope that makes sense.
As #Mysticial pointed out, you need to overload operator>> to do this.
That overload can not be a member of myClass though. It must be either a member of someClass, or else a global overload.
class someClass {
// ...
someClass &operator>>(myClass &);
};
or:
someClass &operator>>(someClass &, myClass &);
If the operator doesn't/can't change the state of the someClass object, you might want to pass the first parameter by const reference (in which case you'd also return a const reference).
Of course, returning a someClass isn't really required, but it's the normally accepted practice for this kind of operator (it allows chaining the operators for something like a >> b >> c;)
>> is the operator. You want to overload operator>>. The signature will look like this:
someClass& operator>>(someClass&, myClass&);
You need to use argument-dependent lookup... I haven't used it myself very often, but you need to overload operator >> with ADL (see the link).
Related
I've got these instructions for an assignment that have put me through a loop here. I need to overload the insertion operator to print out an objects datamembers. However, it states that the overloader has to be a non-friend helper operator.
If that's the case, how can it ever access the private datamembers if its not a 'friend'? And if this is possible, why should I avoid using 'friend'?
Here is what it says word for word:
a helper non-friend operator that inserts the stored string into the left ostream operand.
This operator prefaces the string with the number of the insertion and increment that number
I'm somewhat new to C++ so I really appreciate the help.
If it's not a friend, it needs to use the object's public interface (ergo, you need to write the object's public interface to include the access required by the insertion operator).
For example, you might do something like this:
class thing {
std::string name;
public:
std::string get_name() const { return name; }
// ...
};
std::ostream &operator<<(std::ostream &os, thing const &t) {
return os << t.get_name();
}
Note that I'm definitely not recommending this as good practice--rather the contrary, I think it's often a better idea for the insertion operator to be a friend. But if you're in a class and you're prohibited from doing things the right way, you do what you have to...
Following is the abstraction of string class.
class string {
public:
string(int n = 0) : buf(new char[n + 1]) { buf[0] = '\0'; }
string(const char *);
string(const string &);
~string() { delete [] buf; }
char *getBuf() const;
void setBuf(const char *);
string & operator=(const string &);
string operator+(const string &);
string operator+(const char *);
private:
char *buf;
};
string operator+(const char *, const string &);
std::ostream& operator<<(std::ostream&, const string&);
I want to know why these two operator overloaded functions
string operator+(const char *, const string &);
std::ostream& operator<<(std::ostream&, const string&);
are not class member function or friend functions? I know the two parameter operator overloaded functions are generally friend functions (I am not sure, I would appreciate if you could enlighten on this too) however my prof did not declare them as friend too. Following are the definitions of these function.
string operator+(const char* s, const string& rhs) {
string temp(s);
temp = temp + rhs;
return temp;
}
std::ostream& operator<<(std::ostream& out, const string& s) {
return out << s.getBuf();
}
Could anyone explain this with a small example, or direct me to similar question. Thanks in Advance.
Regards
The friend keyword grants access to the protected and private members of a class. It is not used in your example because those functions don't need to use the internals of string; the public interface is sufficient.
friend functions are never members of a class, even when defined inside class {} scope. This is a rather confusing. Sometimes friend is used as a trick to define a non-member function inside the class {} braces. But in your example, there is nothing special going on, just two functions. And the functions happen to be operator overloads.
It is poor style to define some operator+ overloads as members, and one as a non-member. The interface would be improved by making all of them non-members. Different type conversion rules are applied to a left-hand-side argument that becomes this inside the overload function, which can cause confusing bugs. So commutative operators usually should be non-members (friend or not).
Let's talk about operator +. Having it as a non member allows code such as the following
string s1 = "Hi";
string s2 = "There";
string s3;
s3 = s1 + s2;
s3 = s1 + "Hi";
s3 = "Hi" + s1;
The last assignment statement is not possible if operator+ is a member rather than a namespace scope function. But if it is a namespace scope function, the string literal "Hi" is converted into a temporary string object using the converting constructor "string(const char *);" and passed to operator+.
In your case, it was possible to manage without making this function a friend as you have accessors for the private member 'buf'. But usually, if such accessors are not provided for whatever reason, these namespace scope functions need to be declared as friends.
Let's now talk about operator <<.
This is the insertion operator defined for ostream objects. If they have to print objects of a user defined type, then the ostream class definition needs to be modified, which is not recommended.
Therefore, the operator is overloaded in the namespace scope.
In both the cases, there is a well known principle of Argument Dependent Lookup that is the core reason behind the lookup of these namespace scope functions, also called Koenig Lookup.
Another interesting read is the Namespace Interface Principle
Operators can be overloaded by member functions and by standalone (ordinary) functions. Whether the standalone overloading function is a friend or not is completely irrelevant. Friendship property has absolutely no relation to operator overloading.
When you use a standalone function, you might need direct access to "hidden" (private or protected) innards of the class, which is when you declare the function as friend. If you don't need this kind of privileged access (i.e. you can implement the required functionality in terms of public interface of the class), there's no need to declare the function as friend.
That's all there is to it.
Declaring a standalone overloading function as friend became so popular that people often call it "overloading by a friend function". This is really a misleading misnomer, since, as I said above, friendship per se has nothing to do with it.
Also, people sometimes declare overloading function as friend even if they don't need privileged access to the class. They do it because a friend function declaration can incorporate immediate inline definition of the function right inside the class definition. Without friend one'd be forced to do a separate declaration and a separate definition. A compact inline definition might just look "cleaner" in some cases.
I'm a bit rusty with C++ overloads but I would complete the above answers by this simple memo :
If the type of the left-hand operand is a user-defined type (a class, for instance), you should (but you don't have to) implement the operator overloading as a member function. And keep in mind that if these overloads -- which will most likely be like +, +=, ++... -- modify the left-hand operand, they return a reference on the calling type (actually on the modified object). That is why, e.g. in Coplien's canonical form, the operator= overloading is a member function and returns a "UserClassType &" (because actually the function returns *this).
If the type of the left-hand operand is a system type (int, ostream, etc...), you should implement the operator overloading as a standalone function.
By the way, I've always been told that friend keyword is bad, ugly and eats children. I guess it's mainly a matter of coding style, but I would therefore advice you to be careful when you use it, and avoid it when you can.
(I've never been faced to a situation where its use was mandatory yet, so I can't really tell ! )
(And sorry for my bad English I'm a bit rusty with it too)
Scy
Why I can't create or overload operator := in my class in C++?
Is there are some list operators that I can overload?
I can only overload, or also create some new custom operators?
Because no such operator exists in C++. You cannot roll your own operators because you would need to modify the grammar of the language for the parser to recognize them.
You can find a list of the available operators here or here (or better yet by reading the standard if you can get a copy).
Finally, be advised that overloading operators like there is no tomorrow is a mistake that pretty much every C++ beginner makes; operators are really nothing more than functions, and unless there is a very good case to be made for overloading an operator most of the time it's a better idea to just write a plain function for your class instead. For example, std::string does not have an operator* even though it could be argued that it's convenient to write
string sleepy = string("z") * 40;
The operators you can overload are:
Perhaps you meant the assignment or the equals operator.
class Object{
public:
///Overload The Assignment Operator
Object& operator=(const Object& objectIn);
///Overload The Equals Operator
bool operator == (const Object & rhs) const;
protected:
private:
};
Which C++ operators can not be overloaded at all without friend function?
You only need a friend declaration if:
You define the operator as a standalone function outside the class, and
The implementation needs to use private functions or variables.
Otherwise, you can implement any operator without a friend declaration. To make this a little bit more concrete... one can define various operators both inside and outside of a class*:
// Implementing operator+ inside a class:
class T {
public:
// ...
T operator+(const T& other) const { return add(other); }
// ...
};
// Implementing operator+ outside a class:
class T {
// ...
};
T operator+(const T& a, const T& b) { return a.add(b); }
If, in the example above, the "add" function were private, then there would need to be a friend declaration in the latter example in order for operator+ to use it. However, if "add" is public, then there is no need to use "friend" in that example. Friend is only used when granting access is needed.
*There are cases where an operator cannot be defined inside a class (e.g. if you don't have control over the code of that class, but would still like to provide a definition where that type is on the left-hand side, anyway). In those cases, the same statement regarding friend declarations still holds true: a friend declaration is only needed for access purposes. As long as the implementation of the operator function relies only on public functions and variables, a friend declaration is not needed.
The operators where the left-hand-side operand is not the class itself. For example cout << somtething can be achieved via defining a std::ostream& operator<<(std::ostream& lhs, Something const & rhs); function, and marking them as friend inside the class.
EDIT: Friending is not needed, ever. But it can make things simpler.
The only reason to use friend function is to access the private(including protected) member variable and functions.
You never need a friend function. If you don't want the operator to
be a member (usually the case for binary operators which do not modify
their operands), there's no requirement for it to be a friend. There
are two reasons one might make it a friend, however:
in order to access private data members, and
in order to define it in the class body (even though it is not a
member), so that ADL will find it
The second reason mainly applies to templates, but it's common to define
operators like + and - in a template base class, in terms of +=
and -=, so this is the most common case.
Operator overloading and friendship are orthogonal concepts. You need to declare a function (any function) friend whenever it needs access to a private member of the type, so if you overload an operator as a function that is not a member and that implementation needs access to the private members, then it should be friend.
Note that in general it is better not to declare friends, as that is the highest coupling relationship in the language, so whenever possible you should implement even free function overloads of operators in terms of the public interface of your type (allowing you to change the implementation of the type without having to rewrite the operators). In some cases the recommendation would be to implement operatorX as a free function in terms of operatorX= implemented as a public member function (more on operator overloading here)
There is an specific corner case, with class templates, where you might want to declare a free function operator as a friend of the template just to be able to define it inside the template class, even if it does not need access to private members:
template <typename T>
class X {
int m_data;
public:
int get_value() const { return m_data; }
friend std::ostream& operator<<( std::ostream& o, X const & x ) {
return o << x.get_value();
}
};
This has the advantage that you define a single non-templated function as a friend in a simple straightforward way. To move the definition outside of the class template, you would have to make it a template and the syntax becomes more cumbersome.
You need to use a friend function when this is not the left-hand-side, or alternatively, where this needs to be implicitly converted.
Edit: And, of course, if you actually need the friend part as well as the free function part.
operators [] -> =
Must be a member functions.
Other binary operators acceptable for overloading can be write in function form or in memeber-function form.
Operators acceptable for overloading is all unary and binary C++ operators except
: . :: sizeof typeid ?
It's possible to overload the not operator for a class:
class TestA
{
public:
bool Test;
const bool operator!(){return !Test;}
};
So that...
TestA A; A.Test = false;
if(!TestA){ //etc }
...can work. However, how does the following work?
if(TestA) //Does this have to be overloaded too, or is it the not operator inverted?
I will add, having read it, I am slightly confused by the typedef solution that is employed, and I don't fully understand what is occurring, as it seems somewhat obsfucated. Could someone break it down into an understandable format for me?
You could write an operator bool(). This takes care of coercion to bool, making statements as your above one possible.
You overload operator void* (like the standard library's iostreams) or use boost's trick of using an "unspecified_bool_type" typedef (safe bool). It does NOT automatically invert your operator!