Skip to content

ref readonly parameters C# 12.0performancecorrectness

Allow parameters to be passed by reference without being modified.

A ref parameter means the reference (pointer) to the value is provided to the called method rather than the object or value itself. This is useful if the method needs to modify the caller's variable or if the value is large, such as a big struct, and copying it would be costly.

in parameters C# 7.2 already let a method promise not to modify the value, but they also accept plain values such as new BigStruct(), silently passing a reference to a temporary copy. That makes in a poor fit for APIs that need a real variable, and changing an existing ref parameter to in was a breaking change for callers that pass ref.

In C# 12.0 a parameter can be declared ref readonly: the method cannot modify the value, and callers are expected to pass a variable.

Code ​

csharp
var bigStruct = new BigStruct();
Process(in bigStruct); // or ref bigStruct

Process(new BigStruct()); // warning: argument should be a variable

void Process(ref readonly BigStruct bigStructRef)
{
    // bigStructRef = new BigStruct(); would fail
}
csharp
var bigStruct = new BigStruct();
Process(in bigStruct);

Process(new BigStruct()); // allowed: passes a reference to a temporary copy

void Process(in BigStruct bigStructRef)
{
    // bigStructRef = new BigStruct(); would fail
}

Notes ​

  • Callers pass the argument with ref or in; passing a variable without either, or a value that isn't a variable, produces a warning rather than an error

More information ​

Powered by Intracia