C# 7 Switch Pattern matching

When it comes to switch statements, match expressions were limited to comparing a variable to a constant value (constant pattern). C# 7 supports switch type pattern matching, where case clause can match the type of variable being checked and is no longer limited to numeric types and the string type. 

Now you can switch on any type because restrictions on variable types have been removed from switch expressions. Let’s look at how to implement pattern matching in the following code examples.

Note: You can use return or break statements but type pattern does not support goto statement. Constant pattern supports goto statement.

Switch Pattern Matching Example 1

Let’s create two new classes called Fruit and Vegetable to illustrate the concept of pattern matching in switch statements. The code for the Fruit and Vegetable class is as follows.

public class Fruit
{
    public string Name{get; set;}
    public int Quantity{get; set;}
    
    public Fruit(string name, int quantity){
        Name = name;
        Quantity = quantity;
    }
}

public class Vegetable
{
    public string Name{get; set;}
    public Vegetable(string name){
        Name = name;
    }
}

Now create PrintInfo() method to include a boilerplate code of a switch statement.

public static void PrintInfo(object food)
{
  switch (food)
  {

    default:
      Console.WriteLine("Food info not found.");
      break;
  }
}

Note: The food variable is an object because object type allows for a variable of any type.

C# 7 switch with type pattern

Now, expand the case statement to check for the Fruit and Vegetable types. If an object matches with any of the two types, it then acts on that object and uses its type in the body of the case statement. This allows you to call the type-specific Name and Quantity properties. Let’s change PrintInfo() method to reflect the new changes:

public static void PrintInfo(object food)
{
	switch (food)
	{
		case Fruit item:
			Console.WriteLine($"{item.Name} is a {nameof(Fruit)}. Quantity available {item.Quantity}.");
			break;
		case Vegetable item:
			Console.WriteLine($"{item.Name} is a {nameof(Vegetable)}.");
			break;
		default:
			Console.WriteLine("Food info not found.");
			break;
	}
}

Depending on the type of the food variable, different case statements are matched.

Note: The order of the case clauses is now significant when switching on type.

C# 7 switch with case statement and when clause

Another feature of case statements is the use of when guard, which can be added to perform more specific pattern matching on the variable. Besides checking the type, the value of the type is also checked for a match.For the first case statement in the switch structure below, the item would only be a match if the food is a type Fruit and its Quantity property is equal to 0 and output a different result based on that. Consider the following code.

public static void PrintInfo(object food)
{
	switch (food)
	{
		case Fruit item when (item.Quantity == 0):
			Console.WriteLine($"{item.Name} is a {nameof(Fruit)}. Out of Stock.");
			break;
		case Fruit item:
			Console.WriteLine($"{item.Name} is a {nameof(Fruit)}. Quantity available {item.Quantity}.");
			break;
		case Vegetable item:
			Console.WriteLine($"{item.Name} is a {nameof(Vegetable)}.");
			break;
		default:
			Console.WriteLine("Food info not found.");
			break;
	}
}

C# 7 switch with null case statement

You can also check for null values by adding a null case. This ensures that the argument passed to the switch statement is not null. Now the completed switch statement is as follows.

public static void PrintInfo(object food)
{
	switch (food)
	{
		case Fruit item when (item.Quantity == 0):
			Console.WriteLine($"{item.Name} is a {nameof(Fruit)}. Out of Stock.");
			break;
		case Fruit item:
			Console.WriteLine($"{item.Name} is a {nameof(Fruit)}. Quantity available {item.Quantity}.");
			break;
		case Vegetable item:
			Console.WriteLine($"{item.Name} is a {nameof(Vegetable)}.");
			break;
		case null:
			Console.WriteLine("Invalid food.");
			break;
		default:
			Console.WriteLine("Food info not found.");
			break;
	}
}

Test Code

OUTPUT

Apple is a Fruit. Out of Stock.
Peach is a Fruit. Quantity available 12.
Potato is a Vegetable.
Invalid food.

Switch Pattern Matching Example 2

using System;
using System.Collections.Generic;

public class Program
{
 public static void Main()
 {
       GetType(3);
       GetType("Hi");
       GetType(false);
       GetType(2.5f);
       GetType(new List<string>());
       GetType(null);
       GetType(3.5);
 }

 static void GetType(object obj)
   {
       switch (obj)
       {
           case int i:
               Console.WriteLine($"{i} is an integer.");
               break;
           case string s:
               Console.WriteLine($"{s} is a string.");
               break;
           case bool b:
               Console.WriteLine($"{b} is a Boolean.");
               break;
           case float f:
               Console.WriteLine($"{f} is a float.");
               break;
           case List<string> l:
               Console.WriteLine($"{l} is a List object.");
               break;
           case null:
               Console.WriteLine("Value is null.");
               break;
           default:
               Console.WriteLine("Invalid datatype");
               break;
       }
   }
}

Test Code

OUTPUT

3 is an integer.
Hi is a string.
False is a Boolean.
2.5 is a float.
System.Collections.Generic.List`1[System.String] is a List object.
Value is null.
Invalid datatype

Community Input

💬 What other C# 7 Switch Pattern matching topics should I cover here?

Please use twitter or instagram to share your suggestions. We will add your feedback here.

Resources

  1. switch
  2. Pattern Matching
Sending
User Rating 0 (0 vote)

TidBits

Most Viewed TidBits