◆ private クラスは親クラスに外からアクセスされたときにそのクラスが見えるかどうか

インナークラス使ってるとアクセス可能範囲がわからなくなってきたのでまとめ
public class Class
{
    public class Class11
    {
        public class Class12
        {
            void method()
            {
                var c11 = new Class11();
                var c12 = new Class12();
                var c13 = new Class13();
                var c21 = new Class21();
                var c22 = new Class21.Class22();
                var c23 = new Class21.Class23(); // error
            }
        }

        private class Class13
        {
            void method()
            {
                var c11 = new Class11();
                var c12 = new Class12();
                var c13 = new Class13();
                var c21 = new Class21();
                var c22 = new Class21.Class22();
                var c23 = new Class21.Class23(); // error
            }
        }

        void method()
        {
            var c11 = new Class11();
            var c12 = new Class12();
            var c13 = new Class13();
            var c21 = new Class21();
            var c22 = new Class21.Class22();
            var c23 = new Class21.Class23(); // error
        }
    }

    private class Class21
    {
        public class Class22
        {
            void method()
            {
                var c11 = new Class11();
                var c12 = new Class11.Class12();
                var c13 = new Class11.Class13(); // error
                var c21 = new Class21();
                var c22 = new Class22();
                var c23 = new Class23();
            }
        }

        private class Class23
        {
            void method()
            {
                var c11 = new Class11();
                var c12 = new Class11.Class12();
                var c13 = new Class11.Class13(); // error
                var c21 = new Class21();
                var c22 = new Class22();
                var c23 = new Class23();
            }
        }

        void method()
        {
            var c11 = new Class11();
            var c12 = new Class11.Class12();
            var c13 = new Class11.Class13(); // error
            var c21 = new Class21();
            var c22 = new Class22();
            var c23 = new Class23();
        }
    }
}

namespace 内に private は作れないので Class クラスで囲んでます
namespace 内に private を作っても同じアセンブリからは見えるし 外部のアセンブリから見れないのなら internal と一緒だから使えなくしてる ってところでしょうか


話を戻して上のコードですが
public Class11
    public Class12
    private Class13
private Class21
    public Class22
    private Class23

という構造で各クラスから全部 (6 種類) のクラスのインスタンスを作ろうとしています

結果として作れないのは
Class1X 系から Class23 と
Class2X 系から Class13 です

Class21 は private なのに Class12 から Class22 が見えています

Class11 と Class21 は同じ階層にあるので private な Class21 を Class11 から見えるのはわかります
Class12, Class13 は Class11 の内側にあるので Class21 は見えても変じゃないです
Class21 が見えるのなら その中の public なものはみえるはず ということでしょうか


クラスの public/private はそのクラスが所属するクラスを外部から扱うときに見えるかどうか ということのようです

  • Class23 を Class22 からみたときは親クラス Class21 の内側なので見える
  • Class23 を Class11 からみたときは親クラス Class21 の外側から見ているので見えない
  • Class22 を Class11 からみたときは親クラス Class21 の外側からだけど public なので Class21 を見ることができるなら見える
  • Class21 を Class11 からみたときは親クラス Class の内側からなので見える

という考え方がわかりやすそうです


基本 private なんて存在しない JavaScript ユーザですので 感覚で public/private 考えているので意外と困惑することがあったりします