6

Note: I am using C# 8's Nullable Reference Types. Reference types are, by default NOT nullable.

Suppose I have the following method:

public void TestMethod<T>(T[] items)
{

}

Without using any generic constraints, how can I use the Nullable attributes to specify that the array itself will not be null, but an individual item in the array may be null?

My goal is the following:

  • No warning, due to the array itself being not null: var len = items.Length;
  • Warning, because an individual item can be null: items[0].ToString()
  • No warning, because of the null coalescing operator: items[0]?.ToString()

This code seems to indicate that the array itself can be null, but, if the array itself is not-null, then each array item is also not null:

public void TestMethod<T>([MaybeNull]T[] items)
{

}

I know that using generic constraints will solve this problem - because I could then use T?[] items - but, then I have to create two versions of the class - one for value types and one for reference types. Is there a way to indicate this without using generic constraints?

Mike Christiansen
  • 1,104
  • 2
  • 13
  • 30
  • You already answered your own question: a) reference types are already nullable, b) if you want a generic type that accomodates both, then generic constraints are the way to go :) – FoggyDay Jul 05 '20 at 23:26
  • I am using C# 8.0's nullable reference types. This means that by default, a reference type is *NOT* nullable. However, in this case, I need to convey to the user of the method that a specific array item *IS* nullable. T? does not work, I must use attributes. I am looking for the right attribute to convey this to the user and the compiler. – Mike Christiansen Jul 05 '20 at 23:57
  • In `C# 8` there is no way to express that the type `T` (or elements of the array `T[]`) can be both `nullable reference type` or `nullable value type` without using type constraints `T : class` and `T : struct`. Here are notes of the language design meeting regarding this problem: https://github.com/dotnet/csharplang/blob/master/meetings/2020/LDM-2020-06-17.md#t. Previously design team considered `T??` syntax for this problem (https://github.com/dotnet/csharplang/blob/master/meetings/2019/LDM-2019-11-25.md). But it faced some problems with this syntax. And now it considers other solutions. – Iliar Turdushev Jul 06 '20 at 04:45
  • 1
    Does this answer your question? [Nullable reference types: How to specify "T?" type without constraining to class or struct](https://stackoverflow.com/questions/55975211/nullable-reference-types-how-to-specify-t-type-without-constraining-to-class) – Pavel Anikhouski Jul 06 '20 at 06:19
  • 1
    According to [latest info from LDM](https://github.com/dotnet/csharplang/blob/master/meetings/2020/LDM-2020-06-17.md#t) `where T : default` will be added in C# 9 – Pavel Anikhouski Jul 06 '20 at 06:24
  • 1
    @PavelAnikhouski - That question you linked to covers how to use attributes to indicate `T?`. And, if that is what I was going for, then `[MaybeNull]` would be appropriate. The issue is, I am looking for `T?[]`. `[MaybeNull]T[]` would indicate the same thing as `T[]?` - I need `T?[]`. – Mike Christiansen Jul 06 '20 at 14:55

0 Answers0