C# Properties in Depth
Properties can do more than store a value. A property can compute its answer on each read, and members can shrink to a single expression.
A get-only computed property
Area stores nothing of its own. Each read multiplies the current width and height.
using System;
class Rectangle
{
public int Width { get; set; }
public int Height { get; set; }
public int Area
{
get { return Width * Height; }
}
}
class Program
{
static void Main(string[] args)
{
Rectangle rect = new Rectangle();
rect.Width = 3;
rect.Height = 4;
Console.WriteLine("Area: " + rect.Area);
rect.Width = 5;
Console.WriteLine("Area now: " + rect.Area);
}
}An auto-property with an initializer
The initializer gives the property its starting value at creation. A later assignment replaces it.
using System;
class Pet
{
public string Name { get; set; } = "Pip";
}
class Program
{
static void Main(string[] args)
{
Pet pet = new Pet();
Console.WriteLine(pet.Name);
pet.Name = "Rex";
Console.WriteLine(pet.Name);
}
}Expression-bodied members
The Diameter property and the Describe method each fit in one expression. The arrow replaces the braces and the return keyword.
using System;
class Circle
{
public double Radius { get; set; }
public double Diameter => Radius * 2;
public string Describe() => "Radius " + Radius;
}
class Program
{
static void Main(string[] args)
{
Circle circle = new Circle();
circle.Radius = 2.5;
Console.WriteLine(circle.Diameter);
Console.WriteLine(circle.Describe());
}
}Example
using System;
class Box
{
public int Width { get; set; } = 2;
public int Height { get; set; } = 5;
public int Area => Width * Height;
public int Perimeter() => 2 * (Width + Height);
}
class Program
{
static void Main(string[] args)
{
Box box = new Box();
Console.WriteLine("Area: " + box.Area);
Console.WriteLine("Perimeter: " + box.Perimeter());
}
}Key points
- A computed property stores nothing and calculates its value on every read.
- A get-only property has no set part, so outside code cannot assign it.
- An auto-property can carry an initializer that sets its starting value.
- An expression-bodied member replaces a one-line body with => and the expression.
- The => form works on both methods and properties.
- The expression runs fresh each time the member is used.
In this example, the Box class starts with width 2 and height 5 from its initializers. The Area property is expression-bodied and multiplies the two sides. The Perimeter method is expression-bodied too and adds the sides before doubling. Both members compute fresh values when printed.
Note
The => in a member is not a lambda, even though the arrow looks the same.
Try it Yourself
Edit the code, then press Run.
Running is simulated
Exercise
What does the line `public int Area => Width * Height;` declare?