Learn Access Modifiers in .NET Core

Introduction

Keywords known as "Access Modifiers" describe how a member, class, or datatype in a program is accessible. These are mostly used to prevent unauthorized programs or classes from manipulating data. The six accessibility levels are defined by four access modifiers (public, protected, internal, and private) as follows.

Below is the accessibility table for these modifiers.

  public protected internal protected internal private private protected
Entire program Y N N N N N
Containing class Y Y Y Y Y Y
Current assembly Y N Y Y N N
Derived class Y Y N Y N N
Derived types within the current assembly Y Y Y Y N Y


Public access modifier

Full access to the program is provided. This indicates that these members or types are accessible to other methods or assemblies that have the class reference. When compared to all other access modifiers, this one has the most permissive access level.

Syntax

public TypeName

Example

public class Employee
{
    public int Id { get; set; }
    public string Name { get; set; }
    public int Rank { get; set; }

    public void PrintDetails()
    {
        Console.WriteLine("{0} - {1}", nameof(Id), Id);
        Console.WriteLine("{0} - {1}", nameof(Name), Name);
        Console.WriteLine("{0} - {1}", nameof(Rank), Rank);
    }
}

var employee = new Employee
{
    Id = 1,
    Name = "Jaimin Shethiya",
    Rank = 163
};

employee.PrintDetails();

Class

Private access modifier

The contained class is the only one with access. These members are not allowed to access any other class inside the current assembly or any other assembly.

Syntax

private TypeName

Example

public class Employee
{
    public int Id { get; set; }

    public string Name { get; set; }

    public int Rank { get; set; }

    private int Value;

    public void SetPrivateValue(int value)
    {
        Value = value;
        Console.WriteLine("{0} - {1}", nameof(Value), Value);
        Console.WriteLine();
    }

    public int GetPrivateValue()
    {
        return Value;
    }

    public void PrintDetails()
    {
        Console.WriteLine("{0} - {1}", nameof(Id), Id);
        Console.WriteLine("{0} - {1}", nameof(Name), Name);
        Console.WriteLine("{0} - {1}", nameof(Rank), Rank);
    }
}


var employee = new Employee
{
    Id = 1,
    Name = "Jaimin Shethiya",
};

employee.SetPrivateValue(163);
employee.Rank = employee.GetPrivateValue();
Console.WriteLine();
Console.WriteLine("{0} - {1}", nameof(employee.Rank), employee.Rank);
Console.WriteLine();

employee.PrintDetails();

Console

Get

In the above screenshot, I tried accessing private properties, but it was not allowing me to do so.

Protected access modifier

The class containing this class's member and derived types is the only one with access. It indicates that somewhere in the program, a subclass of the contained class can access the protected members.

Syntax

protected TypeName

Example

public class PermanentEmployee
{
    protected string FullName = "Jaimin Ashvinbhai Shethiya";
}

var emp = new PermanentEmployee();
Console.WriteLine(emp.FullName);

Full name

In the above screenshot, I tried accessing protected properties, but it was not allowing me to do so.

public class Employee : PermanentEmployee
{
    public int Id { get; set; }

    public string Name { get; set; }

    public int Rank { get; set; }

    public void PrintDetails()
    {
        Console.WriteLine("{0} - {1}", nameof(Id), Id);
        Console.WriteLine("{0} - {1}", nameof(Name), Name);
        Console.WriteLine("{0} - {1}", nameof(Rank), Rank);
        Console.WriteLine("{0} - {1}", nameof(FullName), FullName);
    }
}

public class PermanentEmployee
{
    protected string FullName = "Jaimin Ashvinbhai Shethiya";
}

var emp = new Employee
{
    Id = 1,
    Name = "Jaimin",
    Rank = 163
};

emp.PrintDetails();

Print

Internal access modifier

Any class or type specified as internal is accessible anywhere inside the same namespace; access is restricted to the current Assembly. In C#, it is the standard access modifier.

Syntax

Internal TypeName

Example

public class Employee
{
    public int Id { get; set; }

    public string Name { get; set; }

    public int Rank { get; set; }

    internal string FullName { get; set; }

    public void PrintDetails()
    {
        Console.WriteLine("{0} - {1}", nameof(Id), Id);
        Console.WriteLine("{0} - {1}", nameof(Name), Name);
        Console.WriteLine("{0} - {1}", nameof(Rank), Rank);
        Console.WriteLine("{0} - {1}", nameof(FullName), FullName);
    }
}

var emp = new Employee
{
    Id = 1,
    Name = "Jaimin",
    Rank = 163,
    FullName = "Jaimin Ashvinbhai Shethiya"
};

emp.PrintDetails();

Print Detail

Protected internal access modifier

Only the current assembly and the derived types of the contained class are accessible. It indicates that any class, either inside or outside of the current Assembly, that derives from the contained class is permitted access.

Syntax

protected internal TypeName

Example

namespace AccessModifiersDemo
{
    public class Employee
    {
        public int Id { get; set; }
        public string Name { get; set; }
        public int Rank { get; set; }
        internal string FullName { get; set; }
        protected internal string Message = "Hello, ";

        public void PrintDetails()
        {
            var greet = new Greet();
            Console.WriteLine("{0} - {1}", nameof(Id), Id);
            Console.WriteLine("{0} - {1}{2}", nameof(Name), Message, Name);
            Console.WriteLine("{0} - {1}", nameof(Rank), Rank);
            Console.WriteLine("{0} - {1}", nameof(FullName), FullName);
        }
    }
}

namespace AccessModifiersDemo
{
    public class Greet
    {
        protected internal string Message = "Hello, ";
    }
}

namespace AssemblyOne
{
    public class PermanentEmployee : Greet
    {
        internal string FullName = "Jaimin Ashvinbhai Shethiya";

        public void PrintDetail()
        {
            var greet = new Greet();
            Console.WriteLine("{0}{1}", greet.Message, FullName);
        }
    }
}

var employee = new Employee
{
    Id = 1,
    Name = "Jaimin",
    Rank = 163,
    FullName = "Jaimin Ashvinbhai Shethiya"
};

employee.PrintDetails();
Console.WriteLine();

var permanentEmployee = new PermanentEmployee();
permanentEmployee.PrintDetail();

Permanent

Private protected access modifier

The current assembly's containing class and any of its derived types are accessible. Versions 7.2 and later of C# are compatible with this modification.

Syntax

private protected TypeName

Example

namespace AccessModifiersDemo
{
    public class Employee
    {
        public int Id { get; set; }
        public string Name { get; set; }
        public int Rank { get; set; }
        internal string FullName { get; set; }
        private protected string Message = "Hello, ";

        public void PrintDetails()
        {
            var greet = new Greet();
            Console.WriteLine("{0} - {1}", nameof(Id), Id);
            Console.WriteLine("{0} - {1}{2}", nameof(Name), Message, Name);
            Console.WriteLine("{0} - {1}", nameof(Rank), Rank);
            Console.WriteLine("{0} - {1}", nameof(FullName), FullName);
        }
    }
}

var employee = new Employee
{
    Id = 1,
    Name = "Jaimin",
    Rank = 163,
    FullName = "Jaimin Ashvinbhai Shethiya"
};

employee.PrintDetails();

Var Employee

We may access Message from the Greet class since the private protected member is accessible from derived classes in the same assembly.

In another assembly, let's extract a class derived from Greet and attempt to retrieve the name of the private protected field from it. As an illustration.

using AccessModifiersDemo;

namespace AssemblyOne
{

    public class PermanentEmployee : Greet
    {
        internal string FullName = "Jaimin Ashvinbhai Shethiya";

        public void PrintDetail()
        {
            var greet = new Greet();
            Console.WriteLine("{0}{1}", greet.Message, FullName);
        }
    }
}

Assembly

The AssemblyOne code is mentioned above.

A compilation error is encountered in the example above when attempting to access the Message field from the Greet-derived class.

Key Points

  • Since namespaces don't have any access limitations, access modifiers are not permitted.
  • A single accessibility at a time is permitted for the user, with the exception of private protected and protected internal.
  • Top-level types (those that are not nested in other types) can only have internal or public accessibility by default.
  • In the event that a member declaration lacks an access modifier, the context-specific default accessibility is applied.

We learned the new technique and evolved together.

Happy coding!


Similar Articles