In C# 8 one should explicitly mark reference types as nullable.
By default, those types are not able to contain null, kinda similar to value types. While this does not change how things work under the hood, the type checker will require you to do this manually.
Given code is refactored to work with C# 8, but it does not benefit from this new feature.
public static Delegate? Combine(params Delegate?[]? delegates)
{
// ...[]? delegates - is not null-safe, so check for null and emptiness
if (delegates == null || delegates.Length == 0)
return null;
// Delegate? d - is not null-safe too
Delegate? d = delegates[0];
for (int i = 1; i < delegates.Length; i++)
d = Combine(d, delegates[i]);
return d;
}
Here is an example of an updated code (not working, just an idea) leveraging this feature. It saved us from a null-check and simplified this method a bit.
public static Delegate? Combine(params Delegate[] delegates)
{
// `...[] delegates` - is null-safe, so just check if array is empty
if (delegates.Length == 0) return null;
// `d` - is null-safe too, since we know for sure `delegates` is both not null and not empty
Delegate d = delegates[0];
for (int i = 1; i < delegates.Length; i++)
// then here is a problem if `Combine` returns nullable
// probably, we can add some null-checks here OR mark `d` as nullable
d = Combine(d, delegates[i]);
return d;
}