jques
jques

Reputation: 53

Can I do the following in c++

I have two classes namely X and Y ;

       X                                  Y 

    foo ( )                           bar ( )

Y only uses foo function in the X classes. Can I do the following in c++ ?

friend bool Y :: bar ( X & (X :: foo) )

That is Y has a permisson only reaching foo function of the X object?

EDIT : Is X & (X :: foo) usage correct ?

Upvotes: 0

Views: 138

Answers (3)

Benjamin Lindley
Benjamin Lindley

Reputation: 103693

No, you cannot. But you can do the following:

class X_foo_friend;

class X
{
    void foo();
    friend class X_foo_friend;
};

class Y
{
    X x;
public:
    void bar();
};

class X_foo_friend
{
    static void foo(X& x);
    friend void Y::bar();
};

void X::foo() {};
void X_foo_friend::foo(X & x) { x.foo(); }

void Y::bar()
{
    X_foo_friend::foo(x);
}

IMO, this is rather silly. I mean, you're the one designing both X and Y, so you could simply restrict your usage in Y of X's functions.

Upvotes: 0

Chubsdad
Chubsdad

Reputation: 25497

I would possibly explore on the lines of an intermediate proxy using ADL concept. This is of course a partial implementation showing the concept.

namespace XNProxy {
    class XNP;
}

namespace XN
{
    using XNProxy::XNP;

    class X {
        friend void f(X *);
    private:
        void foo() { };
    };

    void f(X* p) {
        X x;
        x.foo();
    }
}

namespace XNProxy 
{
    class XNP { };
    using XN::X;
    void f(XNP *) {
        f((XN::X *)nullptr);
    }
};

namespace YN
{
    class Y {
    public:
        void bar() { 
            XNProxy::XNP x;
            f((XNProxy::XNP*)nullptr);
        }
    };
}

int main() {
    YN::Y y;
    y.bar();
}

Upvotes: 0

jrok
jrok

Reputation: 55395

If I understand you question correctly, you want something like this:

class X;

class Y {
public:
    void bar(X& x);
    void baz(X& x);
};

class X {
    void foo() { }
    friend void Y::bar(X& x);
};

void Y::bar(X& x)
{
    x.foo();
}

void Y::baz(X&)
{
    // the following would be an error
    // baz wasn't befriended with X
    // x.foo();
}

int main()
{
    X x;
    Y y;
    y.bar(x);
}

Note the order of declarations and definitions, you need it like this so you can actually make something useful with X inside Y::bar().

If fail to think of a case where this would be a good idea to do, though. If you fell you only need to befriend "parts" of your classes, then maybe your classes are having too many responsibilities.

Upvotes: 1

Related Questions