0

I'm trying to overload the assignment ('=') operator of a template class, but I need the operator= method to be a friend function.

I though this would be simple, but I'm doing something wrong because the code below causes a compilation error:

error C2801: 'operator =' must be a non-static member

template <typename T>
class IDataStream
{
public:
    friend void operator=(const IDataStream& dataStream)
    {
        // set some private members, e.g.
        // this->{...} = dataStream.{...};
    };
}

Can someone show me the error of my ways- I've become pretty stuck on this :( Thanks.

VettelS
  • 1,204
  • 1
  • 9
  • 17
  • Why does it have to be a `friend`? – David G Nov 19 '14 at 02:21
  • @0x499602D2 Because in operator=, I need to access private members of IDataStream. – VettelS Nov 19 '14 at 02:23
  • 1
    Then what's wrong with it just being a regular member function? Member functions can access private data because they belong to the class itself. Besides, you can't make the assignment operator a non-member function (which you are doing by "befriending" it). – David G Nov 19 '14 at 02:24
  • `operator=` cannot be a non-member. And it always needs two arguments, the implicit `this` and right-hand-side. – Deduplicator Nov 19 '14 at 02:24
  • But member functions have access to private members – mpark Nov 19 '14 at 02:25
  • @0x499602D2 It turns out that tiredness makes me completely incompetent. I'd convinced myself (somehow) that it needed to be a friend, and thought that my error was in the combination of friend and operator overload...which it is also, but that issue should never have arisen in this case. Thanks :) – VettelS Nov 19 '14 at 02:37

3 Answers3

3

Your error is using friend, which changes the function from a member-function to an inline-defined friend-function.

operator= can only be defined as a non-static member-function, and needs two arguments, the implicit this and the explicit right-hand-side.

Deduplicator
  • 44,692
  • 7
  • 66
  • 118
1

Let's take a look at the C++ standard.

§ 9.3/1 Functions declared in the definition of a class, excluding those declared with a friend specifier (11.3), are called member functions of that class. A member function may be declared static in which case it is a static member function of its class (9.4); otherwise it is a non-static member function of its class (9.3.1, 9.3.2).

§ 13.5.3/1 An assignment operator shall be implemented by a non-static member function with exactly one parameter. [..]

So you cannot make operator= a friend.

In § 11 [class.access]:

1 A member of a class can be

— private; that is, its name can be used only by members and friends of the class in which it is declared.

Since a member function is a member of the class, it doesn't require the friend specifier to access private data members.

If you want to learn the proper way to overload an operator, please see 's Operator overloading, although the meat of overloading operator= is covered in What is the copy-and-swap idiom?.

Community
  • 1
  • 1
0

As pointed out by 0x499602D2, operator= doesn't need to be a friend function. I'm blaming tiredness for managing to completely overlook that objects have access to private & protected members of objects of the same class...

VettelS
  • 1,204
  • 1
  • 9
  • 17