5

I've got a following code written in C++:

#include <iostream>

using namespace std;

class Window;
class Level
{
    int level;
    int get(Window& w);
public:
    Level(void): level(3) {}
    void show(Window& w);
};

void Level::show(Window& w)
{
    cout << get(w) << endl;
}

class Item
{
    static const int item = 8;
};

class Window
{
    friend int Level::get(Window& w);
    int window;
public:
    Window(void): window(2) {}
    void show(void);
};

void Window::show(void)
{
    cout << "window" << endl;
}

int Level::get(Window& w)
{
    return w.window + level;
}

int main()
{
    Window wnd;
    Level lvl;
    wnd.show();
    lvl.show(wnd);
    cin.get();
    return 0;
}

I want to have access to private member of class Window only accessible by friend function get, which is also private function of class Level. When I'm trying to compile I've got an error C2248. Is that possible to make private function as friend of other class?

Cory Kramer
  • 114,268
  • 16
  • 167
  • 218
Gucu112
  • 877
  • 10
  • 12
  • 2
    some indentation might help – iavr Feb 27 '14 at 17:52
  • Try making `Level` friends with `Windows` i.e. add the `friend class Window` to `class Level`. – imreal Feb 27 '14 at 17:59
  • @Gucu112 nice :-) Now, `friend class Window;` within `Level` or conversely `friend class Level;` within `Window` would do the job. What would be the problem in this? – iavr Feb 27 '14 at 17:59
  • I know I can do that using friend between classes, but I'm looking for a way to access only what I want from `Window` that can be done only by class `Level`. – Gucu112 Feb 27 '14 at 18:01
  • @Gucu112 I am not sure if this can be done or if it pays off the needed complexities in design. But for sure you may e.g. have `Level` derive a `Base` class that contains `get` and is a friend of `Window`. – iavr Feb 27 '14 at 18:07
  • @Gucu112 Btw, now `Level::get` has access to the entire class `Window`, not "only what you want". – iavr Feb 27 '14 at 18:10
  • @iavr Yes you're right, but I've got access to other class only in this function and that's what I'm looking for ;) – Gucu112 Feb 27 '14 at 18:29
  • Possible duplicate of [Why can't a PRIVATE member function be a friend function of another class?](http://stackoverflow.com/questions/26956176/why-cant-a-private-member-function-be-a-friend-function-of-another-class) – Ruslan Jan 08 '16 at 10:26

2 Answers2

4

If I read the standard right, this looks like a compiler bug (unusual I know).

11.3/5:

When a friend declaration refers to an overloaded name or operator, only the function specified by the parameter types becomes a friend. A member function of a class X can be a friend of a class Y.

Note that it doesn't say "public member function", just "member function". To me this implies that the privacy of the friendship-receiving function shouldn't be relevant to the granting of friendship.

Mark B
  • 95,107
  • 10
  • 109
  • 188
  • 1
    "Reading" the standard is beyond me unfortunately, but I confirm that the code in the question fails in both GCC and Clang. – iavr Feb 27 '14 at 18:22
1

Must friend declaration names be accessible? quotes the standard wording that "[a] name nominated by a friend declaration shall be accessible in the scope of the class containing the friend declaration", and gives a rationale for the existence of that (somewhat odd-looking) rule.

  • TL;DR: _in such cases, an easy workaround is simply to befriend the entire class rather than the specific member function_ - issue closed 20 years ago LOL :D Thank you @Stephan for linking it :) – Gucu112 Jan 04 '20 at 15:28