Skip to main content

Documentation Index

Fetch the complete documentation index at: https://docs.syntblaze.com/llms.txt

Use this file to discover all available pages before exploring further.

The ?? operator, formally known as the null-coalescing operator, returns the value of its left-hand operand if it is not null; otherwise, it evaluates the right-hand operand and returns its result.
leftOperand ?? rightOperand

Technical Characteristics

Operand Constraints The left-hand operand must be a reference type, a nullable value type (Nullable<T> or T?), or, starting with C# 8.0, an unconstrained type parameter (T). Type Resolution The return type of the expression a ?? b (where a is of type A and b is of type B) is determined at compile-time by evaluating available implicit conversions in the following strict order of precedence:
  1. If A is a nullable value type and an implicit conversion exists from B to the underlying type of A, the result type is the underlying type of A. For example, evaluating int? ?? int yields a result type of int.
  2. Otherwise, if an implicit conversion exists from B to A, the result type is A.
  3. Otherwise, if an implicit conversion exists from A (or its underlying type if A is a nullable value type) to B, the result type is B. For example, evaluating string ?? object yields a result type of object.
Short-Circuit Evaluation The ?? operator utilizes short-circuit evaluation. The right-hand operand is evaluated strictly if and only if the left-hand operand evaluates to null. If the left-hand operand is non-null, the right-hand operand is bypassed entirely. Associativity and Evaluation Order The operator is right-associative. An expression chained with multiple null-coalescing operators is parsed and grouped from right to left (e.g., a ?? b ?? c is grouped as a ?? (b ?? c)). However, operand evaluation is strictly left-to-right. The left-most operand (a) is evaluated first; if it is not null, the entire right side (b ?? c) is short-circuited and never evaluated. Throw Expressions Since C# 7.0, the right-hand operand of the null-coalescing operator can be a throw expression. This allows the program to throw an exception directly during evaluation if the left-hand operand evaluates to null.

Syntax Visualization

using System;

public class NullCoalescingDemonstration
{
    public static void Main()
    {
        // 1. Nullable value type resolution (Result type is the underlying type: int)
        int? nullableInt = null;
        int fallbackInt = 5;
        int result1 = nullableInt ?? fallbackInt; 

        // 2. Reference type resolution with implicit conversion (Result type: object)
        string nullString = null;
        object fallbackObject = new object();
        object result2 = nullString ?? fallbackObject; 

        // 3. Right-associativity with left-to-right evaluation
        int? x = null;
        int? y = null;
        int z = x ?? y ?? 10; // Parsed as x ?? (y ?? 10), returns 10

        // 4. Short-circuit evaluation
        string validString = "initialized";
        // ExpensiveMethod() is never invoked because validString is not null
        string result3 = validString ?? ExpensiveMethod(); 

        // 5. Throw expression (C# 7.0+)
        string missingValue = null;
        try
        {
            string result4 = missingValue ?? throw new ArgumentNullException(nameof(missingValue));
        }
        catch (ArgumentNullException)
        {
            // Exception is caught here
        }
    }

    // 6. Unconstrained type parameter (C# 8.0+)
    public static T GetValueOrDefault<T>(T value, T defaultValue)
    {
        // T is not constrained to class or struct
        return value ?? defaultValue; 
    }

    // Method stub required for the short-circuit evaluation example
    private static string ExpensiveMethod()
    {
        Console.WriteLine("ExpensiveMethod was called.");
        return "expensive result";
    }
}
Master C# with Deep Grasping Methodology!Learn More