Using Cast and OfType in C# LINQ
In C# LINQ, Cast<T> and
OfType<T> are standard query operators used to handle
collections containing mixed or unspecialized types, such as legacy
ArrayList objects or collections of interfaces. While both
operators attempt to convert elements into a strongly typed
IEnumerable<T>, they handle incompatible elements
fundamentally differently: Cast<T> strictly attempts
an explicit conversion on every item and throws an exception on failure,
whereas OfType<T> silently filters the collection,
returning only the elements that match the target type.
The Cast Operator
The Cast<T> operator attempts to cast every
element in a sequence to the specified type T. It uses
standard explicit casting ((T)item) internally. If an
element cannot be cast to the target type, the runtime throws an
InvalidCastException.
Use Cast<T> when you expect every element in an
untyped collection to be of the specified type and want the operation to
fail immediately if an unexpected type appears.
using System;
using System.Collections;
using System.Linq;
ArrayList mixedList = new ArrayList { 10, 20, 30 };
// Successfully casts all elements to an IEnumerable<int>
var numbers = mixedList.Cast<int>();
foreach (var num in numbers)
{
Console.WriteLine(num);
}
// Throws InvalidCastException because "Hello" cannot be cast to int
ArrayList brokenList = new ArrayList { 10, "Hello", 30 };
var failingQuery = brokenList.Cast<int>().ToList(); The OfType Operator
The OfType<T> operator filters elements based on
the specified type T. It checks each element using the
is T type-testing pattern. If an element cannot be assigned
to type T, it is omitted from the resulting sequence rather
than throwing an exception.
Use OfType<T> when handling heterogeneous
collections where you only want to process a specific subset of
elements.
using System;
using System.Collections;
using System.Linq;
ArrayList heterogeneousList = new ArrayList { 42, "Apple", 84, "Banana", true };
// Filters and returns only string elements: "Apple", "Banana"
var stringsOnly = heterogeneousList.OfType<string>();
foreach (var text in stringsOnly)
{
Console.WriteLine(text);
}Key Differences
| Feature | Cast<T> |
OfType<T> |
|---|---|---|
| Failure Handling | Throws
InvalidCastException |
Skips incompatible elements |
| Internal Mechanism | Explicit cast:
(T)element |
Type check: element is T |
| Output Size | Always matches source collection size (if successful) | Size can be less than or equal to source |
| Primary Use Case | Transitioning untyped collections to generic types | Filtering heterogeneous collections |
Choosing Between Cast and OfType
Choose Cast<T> when converting legacy collections
(like ArrayList or ControlCollection) where
all items are guaranteed to share the same type, and an invalid item
indicates a critical data error.
Choose OfType<T> when you want to filter a
polymorphic collection to extract only specific derived classes, such as
selecting only Button instances from a collection of
Control objects.