Readonly keyword In C#

Readonly keyword is a modifier in C# when it applied to a field, the value of the field can be assigned at the time of declaration or in constructor only not in any other methods. After that we cannot change the value.

But most of the people I discussed will compare it with constant field. But Readonly field is different from constant field. And often it is misunderstood.

And Readonly modifier can be applied only to the Fields not local variables.

First of all Readonly value is not constant it may be different depending upon object created. So its Constant to the object created

On this page

Readonly field in C#:

As mentioned above we can assign the C# readonly fields in constructor. But a class may be having multiple constructors, in that case, the value will be different depending upon the constructor used.

Please see the following example

public class ReadonlyClass
{
  // Assing a readonly field
  public readonly int discount;

  public ReadonlyClass()
  {
    discount = 10;
  }
  
  public ReadonlyClass(int _discount)
  {
    discount = _discount;
  }
}

For example, a customer gets by default 10% discount on the product. Often in some special cases if we want to increase the discount or decrease the discount we will use another constructor to create an object.

var customer1 = new ReadonlyConstant.ReadonlyClass();

Console.WriteLine("Discount :{0}",customer1.discount);

//Discount : 10

var customer2 = new ReadonlyConstant.ReadonlyClass(20);

Console.WriteLine("Discount :{0}", customer2.discount);

//Discount : 20

//customer1.discount = 5; This is wrong

//customer2.discount = 10; This is wrong

So for the customer1 discount is 10 and it is constant to the customer 1. For customer 2 discount is 20 and it is constant for the customer 2.

After assigning the value in constructor we cannot change it it will show following error.

So the readonly field value constant to the object created. To make it constant across the object add static keyword.

I explained about static readonly in differences between constant vs readonly variables article.

We can pass C# readonly fields as ref or out parameters in Constructor Context:

As the readonly fields can be assigned inside the constructor we can pass them as ref or out parameters inside the constructor context as shown below.

public class Program
{
 public readonly int z = 5;
 public readonly int y;
 public static readonly int x = 1;
 
 static void printOut(out int v)
 {
  v= 0;
  Console.WriteLine(v);
 }

 static void printRef(ref int v)
 {
  v = 90;
  Console.WriteLine(v);
 }

 public void NormalMethod()
 {
    //printOut(ref y); This is wrong
    //printRef(out y);
 }

 //Normal Constructor
 public Program()
 {
  y = 9;
  z = 90;
  z = 9000;
  printOut(out z);
  printRef(ref z);
  //The value of y is 90
 }

 //Static constructor
 static Program()
 {
   x = 3;
   x = 9;
   printOut(out x);
   printRef(ref x);
   //The value of x is 90
 }
}

But we cannot pass them in any other methods in above example we cannot pass readonly field y in NormalMethod() as ref or out parameter because its not in constructor context.

Understand difference between ref and out parameters in c#

Do not declare mutable types like arrays collections as readonly in C#:

Please go through the following article

Difference between readonly, constant and static readonly in C#

As mentioned above article in differences we should not assign mutable types to readonly because only the reference cannot be changed but the object that holds can be changed.

Please see the below example.

public class ReadonlyCollection
 {
  public readonly List<int> readonList;

  public ReadonlyCollection()
 {
   readonList = new List<int>() {1,2};
 }

}

var readcollection = new ReadonlyCollection();

readcollection.readonList[0] = 3;

readcollection.readonList[1] = 4;

//But this is wrong
//readcollection.readonList = new List<int>();

We can change the values of readonly list as shown above.

But If we you want to assign it to new collecation it will throw error because only reference is immutable not the object that holds.

I hope this article clears the most common doubts about Readonly keyword modifier in C#.