Property Accessors
In C# a property accessors define how a class exposes its internal fields. To better understand this let's take a look at the individual definitions of these concepts.
-
Field : The direct variable inside a class, typically declared with an access modifier (private, public, etc.).
-
Property: The construct that provides controlled access to a field through accessors.
-
Accessor: The individual
get
orset
block within a property.
Standard Usage
The standard approach to using property accessors is where both a getter and setter are explicitly defined, using a private field to store the value. The getter returns the value, and the setter modifies it. Below of how this is implemented:
public class Person
{
private string _name; // Private field
public string Name // Public property
{
get { return _name; } // Getter (accessor): Returns the value of _name
set { _name = value; } // Setter (accessor): Assigns a new value to _name
}
}
We can break the code above into the following elements:
_name
is the field accessible only to this class as it is marked asprivate
Name
is thepublic
property which other classes can access, but to what extent?get
andset
are the accessors. Which in this instance allows for the value the field to be viewed and for a new value to the filed to be set.
Have you ever been asked to fill out a survey or complete a form? Whether it was a digital form or an old-school paper one, you probably encountered a series of questions with little boxes where you had to type or write your answers.
Think of one of these boxes as a field, let's say it is labeled "Name." The field itself is just an empty container, waiting for someone to enter a value like "Bob" or "Sue".
Now, when it’s time to compile the responses, we are not interested in the textbox itself, instead we want the actual value that was entered. That's where properties come in! The property called Name
lets us retrieve what was written in the box.
Interacting with Data
Just like some forms say "Do not write in this section", property accessors determine how we can interact with the data.
-
If the form is read-only, it’s like having a property with only a
get
accessor. We can read the value ofName
, but that is all we can do. -
If we notice a typo and need to correct it, this is where we could use
set
accessor, which allows the value ofName
to be changed or updated. -
And if a field is completely locked down with a private setter, this means only the form has access to the
field
textbox and the input value. No one outside the actual form has access to the data, and you’ll just have to live with your mistakes.
So next time you’re filling out a form, just remember: fields hold data, properties manage data, and accessors decide whether you're allowed to mess the data.
And if you ever get frustrated with a form that won’t let you correct your own name, just know, somewhere in the code, there are property accessors at work or in some cases not at work 😅 that limit your access.
Auto Backing Field
As in the previous examples a private
field is defined and then a public
property to access the field is defined.
However, since this field property relationship is very common, C# allows or a more concise way to define a property without manually creating a private field:
public string Name { get; set; } // Auto-property (C# automatically creates a backing field)
In this example, the private backing field (like _name
) is not explicitly declared because C# automatically creates it behind the scenes to store the value. You can think of this backing field as a memory location where the value of Name
is stored.
In code, the backing field is never directly accessed. Instead, the value is always accessed through the property Name
(using the get
and set
methods). While the backing field is not visible in your code, it exists internally to handle the storage of the value.
How to Use
If we take another look at the previous example, in which C# creates the backing field, and both a get and set accessor are applied to the property, it actually isn't really all that usefully.
public string Name { get; set; } // Auto-property (C# automatically creates a backing field)
In fact the property we created could have simply been a public
field as in the example below:
public string Name;
Okay, so why should we use property accessors at all? The real value of using property accessors is when we want to control to access (get/set) the property. In fact there are several different ways in which we can control access to properties, which include:
Read-Only Property
private string _name;
public string Name
{
get { return _name; }
}
Description:
A read-only property means the value can only be retrieved publicly through the get
accessor. The private field (_name
) can be set only within the class, typically in the constructor or other methods.
Read-Only | Auto Field
public string Name { get; private set; }
Name = "Bob";
Description:
This combines the auto backing field syntax with a private setter, allowing public access to the value via get
but restricting the setter to within the class. The compiler automatically creates the backing field for storing the value.
Using the auto-backed field method with a private set, as shown in the example above, is perfectly valid. However, relying solely on the public property within the class might lead us to mistakenly believe that it's a public field accessible by all classes. While we could always scroll to the top of the code or check our IDE for clarification, manually defining a private field within the class ensures that we explicitly understand the field is encapsulated and not accessible from outside the class.
Write-Only Property
private string _password;
public string Password
{
set { _password = value; }
}
Description:
A write-only property has a setter but no getter, which is useful for cases like storing sensitive data (e.g., passwords) where the value is only set and not retrieved.
Custom Setter Logic
private string _age;
public string Age
{
get { return _age; }
set { if (value > 0) _age = value; }
}
Description:
This property adds custom logic in the setter, allowing validation before setting the value. In this case, the age can only be set to positive values.
Expression-Bodied Property
private string _score;
public string Score
{
get => _score;
set => _score = value;
}
Description:
An expression-bodied property is a shorthand syntax for properties where the getter and/or setter is a simple single expression. It's compact and typically used when there's no need for additional logic in the getter or setter.
Conclusion:
Each property style serves different purposes, from full control over getter/setter logic to more concise forms. Choose the one that fits the needs of your class and its logic.