Artur S.
Artur S.

Reputation: 334

Is there a better way to deal with nullable return that depends on another value?

I have a method that returns a tuple (MyEnum, MyObject?). There is one and only one enum value that means MyObject is not null - all the others mean MyObject will be null (and the string will have a message).

Something along the lines of

(MyEnum response, Package? package) MyMethod()
{
    if (Today == NiceDay)
    {
        return (MyEnum.Happy, new Package("I'm happy!"));
    }
    if (Today == RainyDay)
    {
        return (MyEnum.Pensive, null);
    }
    if (Today == SnowyDay)
    {
        return (MyEnum.Cold, null);
    }
}

Obviously, if I try and use MyMethod().package.message, the compiler will warn me about the possibility of a null reference. I'm aware of the null-forgiving operator, but that kind of feels like a quick-fix.

Is there a way to "tell" the compiler to expect a value when MyMethod().response is MyEnum.Happy, and null when it is any other value, or is the null-forgiving operator the correct and expected way to deal with this situation?

Upvotes: 0

Views: 136

Answers (3)

Guru Stron
Guru Stron

Reputation: 141845

Currently attributes for null-state static analysis interpreted by the C# compiler do not support neither specifying nullability of selected properties of returned value nor scenario when specific constant/enum value can be tied to nullability of parameters (except bool constants). The closest thing which can be done - return boolean value and tie out parameter to the return:

bool MyMethod(out MyEnum response, [NotNullWhen(true)] out Package? package)
{
    string Today = "";
    response = MyEnum.Happy;
    package = new Package("");
    return true;
}

Usage:

if(MyMethod(out _, out var packageValue))
{
    Console.WriteLine(packageValue.ToString()); // no warning
}

Upvotes: 2

Vlad
Vlad

Reputation: 2565

As a suggestion to resolve the issue, instead of the null have a static property in the Package class that defines an empty package:

class Package {
    public static Package None => new Package { Message = "No package." };
}

In your code make the return for Package non-nullable and use

   return (MyEnum.Pensive, Package.None);

Upvotes: 0

Muhammad Hunain
Muhammad Hunain

Reputation: 106

So there are many ways to handle null/null warnings.

First If you are 100% sure that the value cannot be null here you can use ! operator something like this package!.Message

Second If You are not sure and there is only one condition in which the value can not be null its better to use the ternary operator like this var result = MyMethod().response == MyEnum.Happy ? MyMethod().package.message : string.Empty;

Third you can use ?? operator like this var message = MyMethod().package?.message ?? "No message found"; or empty string according to your use case.

Upvotes: 2

Related Questions