2

I'm a C++ developer learning C#, and I'm in a situation where I need a class C to have two members that belong to it that represent "robots." The robots need to be able to access private members of C, and they don't need to be used anywhere else. In C++ I'd use the "friend" keyword, but I don't know what to do here. I thought about doing something like this:

class C
{
    private Member mem;
    private Robot bot;

    private class Robot
    {
        C owner;
        public void function() { //Robot needs to use owner.mem here, 
                                 //but can't because it's private}
    };
}

The trouble is that I don't know how to say that a Robot is "owned" by an instance of C, and can access its members.

  • I'm not sure what you are trying to say in the comment, because that is false. `owner.mem` would be accessible in `function`. – Mike Zboray Jan 15 '16 at 03:25
  • 1
    In your case, Robot members can access C private members. Try it and see. If you can't make it work, please post the exception. – mbm Jan 15 '16 at 03:45
  • "but can't because it's private" - please post code that demonstrates the problem (as it is wrong in current state). Comment is not enough to see what exact problem you have. Note: that if you'd be coming from Java background you may expect nested class to have reference to its parent for free, but there is no case of it in C++ - so need [MCVE] to clarify problem. – Alexei Levenkov Jan 15 '16 at 04:26

3 Answers3

2

One way to do it is to pass the outer class's instance to the inner class's constructor as a reference.

class C
{
    private Member mem;
    private Robot bot;

    private class Robot
    {
        C owner;
        public Robot(C c) {owner = c;}
        public void function()
        { 
           // Robot can use owner.mem here
        }
    };
}
Ilian
  • 5,113
  • 1
  • 32
  • 41
liusy182
  • 205
  • 1
  • 7
1

There's no direct equivalent of friend - the closest that's available (and it isn't very close) is InternalsVisibleToAttribute but it breaks the relationships between classes and undermines some fundamental attributes of an OO language.

The only decent solution that has occurred to me is to invent an interface, ICClass, which only exposes the public methods, and have the Factory return ICClass interfaces.

This involves a fair amount of tedium - exposing all the naturally public properties again in the interface.

Mohit S
  • 13,723
  • 6
  • 34
  • 69
1

There are heaps of threads about this: Why does C# not provide the C++ style 'friend' keyword?

"Robot needs to use owner.mem here, but can't because it's private"

I think you want Protected with an inheritance model:

class C
{
    protected Member mem;
    protected Robot bot;
}

private class Robot : C
{
   public void function() { 
      base.mem...  // here you can use the base classes mem and bot
   };
}
Community
  • 1
  • 1
Jeremy Thompson
  • 61,933
  • 36
  • 195
  • 321
  • You can also see the Skeets answer to C#'s equivilent of "C++'s Friend" - its the same as @MohitShrivastava mentions: http://stackoverflow.com/questions/204739/what-is-the-c-sharp-equivalent-of-friend – Jeremy Thompson Jan 15 '16 at 03:32
  • This answer implies that `private` is not accessible and this is wrong, so the answer is wrong. – radarbob Jan 15 '16 at 03:38
  • And suggesting that using `protected` is the solution is even more wrong. – Ilian Jan 15 '16 at 03:40
  • @lonewolf and @radarbob - I edited it to clear up the confusion around suggesting `protected`, cheers – Jeremy Thompson Jan 15 '16 at 04:05
  • @Rob yes, as per your intuition I did misinterpret at first - now I've cleaned up my answer so its using inheritance rather than nesting with the recommended `protected` – Jeremy Thompson Jan 15 '16 at 04:08