Access Modifiers in C#

Last Updated : 20 Mar, 2026

Access modifiers in C# define the scope and visibility of classes, methods, fields, constructors and other members. They determine where and how a member can be accessed in a program.

Access Modifiers and Accessibility

There are 6 access modifiers (public, protected, internal, private, protected internal, private protected) as follows:

Modifiers

Entire program

Containing Class

Current assembly

Derived Types

Derived Types within Current Assembly

public

Yes

Yes

Yes

Yes

Yes

private

No

Yes

No

No

No

protected

No

Yes

No

Yes

Yes

internal

No

Yes

Yes

No

Yes

protected internal

No

Yes

Yes

Yes

Yes

private protected

No

Yes

No

No

Yes

1. public Modifier

Accessible from anywhere in the project or other assemblies (if referenced). public is suitable for members that need to be globally available. Example:

C#
using System;

class Student
{
    public int rollNo;
    public string name;

    public Student(int r, string n)
    {
        rollNo = r;
        name = n;
    }

    public int getRollNo()
    {
        return rollNo;
    }

    public string getName()
    {
        return name;
    }
}

class Geeks
{
    static void Main(string[] args)
    {
        Student S = new Student(1, "Geek");

        // accessible through another method       
        Console.WriteLine("Displaying using class members");
        Console.WriteLine("Roll number: {0}", S.rollNo);
        Console.WriteLine("Name: {0}", S.name);

        Console.WriteLine();

        Console.WriteLine("Displaying Using methods");
        Console.WriteLine("Roll number: {0}", S.getRollNo());
        Console.WriteLine("Name: {0}", S.getName());
    }
}

Output
Displaying using class members
Roll number: 1
Name: Geek

Displaying Using methods
Roll number: 1
Name: Geek

2. private modifier

When we use private modifier, member is accessible only within the same class. Default modifier for class members if none is specified is private. It It is used for encapsulation of data. Example:

C#
using System;

class Parent 
{	
	private int value; // private field

	public void setValue(int v) // setter
	{
		value = v;
	}

	public int getValue() // getter
	{
		return value;
	}
}

class Child : Parent 
{
	public void showValue()
	{
		// Direct access not allowed (private in Parent)
		// Console.WriteLine("Value = " + value);
	}
}

class Geeks 
{
	static void Main(string[] args)
	{
		Parent obj = new Parent();

		// obj.value = 5; // not allowed
		obj.setValue(4); 
		Console.WriteLine("Value = " + obj.getValue()); 
	}
}

Output
Value = 4

3. protected Modifier

protected access modifier allows members to be accessible within the class and by derived classes (subclasses). It does not allow access from outside the class or its derived classes. Example:

C#
using System;

// Base Class
class Student 
{  
    // Accessible to this class and derived classes
    protected string name; 
  
    public Student(string studentName)
    {
        name = studentName; 
    }
}

// Derived Class
class Geek : Student 
{
    // Constructor calls the base class constructor using : base()
    public Geek(string geekName) : base(geekName) 
    { 
     
    }
  
    public string GetName()
    { 
        return name; 
    }
}

class Geeks 
{
    static void Main(string[] args)
    {
        Geek obj = new Geek("Geeky");
        
        // We call GetName() because 
        // 'name' itself isn't directly 
        // accessible here in the Main method.
        Console.WriteLine("The student's name is: {0}", obj.GetName());
    }
}

Output
The student's name is: Geeky

4. internal Modifier

Accessible only within the same assembly (project). Not visible to other assemblies unless explicitly exposed with InternalsVisibleTo. Example:

C#
// Inside the file Geeks.cs
using System;

// Declare class Complex as internal
internal class Complex 
{
	int real;
	int img;

	public void setData(int r, int i)
	{
		real = r;
		img = i;
	}

	public void displayData()
	{
		Console.WriteLine("Real = {0}", real);
		Console.WriteLine("Imaginary = {0}", img);
	}
}

class Geeks 
{
	static void Main(string[] args)
	{
		// Instantiate the class Complex in separate class but within the same assembly
		Complex c = new Complex();

		// Accessible in class Program
		c.setData(2, 1);
		c.displayData();
	}
}

Output
Real = 2
Imaginary = 1

5. protected internal

It is the combination of protected and internal. Members are accessible within the same assembly and also by derived classes (even if they are in a different assembly). Example:

C#
using System;

public class Parent
{
    // Declared as protected internal
    protected internal string message = "Hello from Parent!";
}
class AnotherClass
{
    public void Display()
    {
        Parent obj = new Parent();
        // Accessible here because we are in the same assembly
        Console.WriteLine(obj.message);
    }
}
class Program
{
    static void Main()
    {
        AnotherClass another = new AnotherClass();
        another.Display();
    }
}

Output
Hello from Parent!

6. private protected Modifier

private protected access is only granted to the containing class. Any other class inside the current or another assembly is not granted access to these members. This modifier is valid in C# version 7.2 and later. Example:

C#
using System;

namespace PrivateProtectedAccessModifier 
{
	class Parent 
	{
		private protected int value;

		public void setValue(int v) 
		{
			value = v;
		}

		public int getValue() 
		{
			return value;
		}
	}
	class Child : Parent 
	{
		public void showValue()
		{
			// accessible in derived class
			Console.WriteLine("Value = " + value);
		}
	}
	class Program 
	{	
		static void Main(string[] args)
		{
			Parent obj = new Parent();

			// obj.value = 5; // not allowed
			obj.setValue(4); 
			Console.WriteLine("Value = " + obj.getValue());
		}
	}
}

Output:

Value = 4

Key Points

  • Namespaces doesn’t allow the access modifiers as they have no access restrictions.
  • The user is allowed to use only one accessibility at a time except the private protected and protected internal.
  • The default accessibility for the top-level types (that are not nested in other types, can only have public or internal accessibility) is internal.
  • If no access modifier is specified for a member declaration, then the default accessibility is used based on the context.
Comment

Explore