取消引用可为空类型

问题描述 投票:0回答:2

我编写了一个函数,将一些参数解析为有效的“事物”。如果参数不能被解析为有效的东西,那么这个函数将返回 null。

我通过将其强制转换为特定类型来访问有效的“事物”,但我想知道是否有一种简洁的方法来“取消引用”该事物而不是强制转换。

private Nullable<Thing> GetTheThing(string arg) 
{
    if (s == "") 
    {
        return new Thing(...);
    } 
    else 
    {
        return null;
    }
}

// ...snip...

var t = GetTheThing("asd")

if (t == null) 
{
    throw Exception("Thing could not be made from this arg");
}

// This function take a "Thing" as it's argument, NOT a NULLABLE.
// Casting just seems so brute force, I feel like t should already know what it is, and I've checked for null, so why can't I just do something like *t?
DoSomethingWithTheThing((Thing)t);
c#
2个回答
0
投票

通常我会这样写:

var maybeThing = MaybeGetThing("asd");
if (maybeThing is not { } thing)
    throw Exception("Thing could not be made from this arg");

// do something with thing which will be non-nullable

MaybeGetThing
(也可以命名为
GetThingOrDefault
GetThingOrNull
):

Thing? MaybeGetThing(string arg) {
   if (arg == ...)
      return null;

   return new Thing(...);
}

其他一些也可能有用的:

Thing GetThingOrThrow(string arg) {
   var maybeThing = MaybeGetThing(arg);
   if (maybeThing is not { } thing)
      throw ...;

   return thing;
}

bool TryGetThing(string arg, [MaybeNullWhen(false)] out Thing result) {
   result = MaybeGetThing(arg);
   return result is { };
}

bool CantGetThing(string arg, [MaybeNullWhen(true)] out Thing result) {
   result = MaybeGetThing(arg);
   return result is null;
}

当您以错误的方式使用时,

MaybeNullWhen
属性应该提供 IDE 警告。

示例:

if (CantGetThing("arg", out var thing)) {
   // can't use thing, it is null
   return;
}
// can use thing since we returned in the case that it was null

-1
投票

您可以在没有变量的情况下完成此任务。

using System;
                    
public class Program
{
    public static void Main()
    {
        if (TryGetTheThing("thing", out Thing thing))
        {
            Console.WriteLine("I got a thing here");
        }
        else
        {
            Console.WriteLine("Thing will be null");
        }   
    }
    
    public static bool TryGetTheThing(string s, out Thing thing)
    {
        if (s == "thing")
        {
            thing = new Thing();
            return true;
        }
        else
        {
            thing = null;
            return false;
        }
    }
}

public class Thing
{
}

工作小提琴在这里

但是如果你坚持让它可以为空,那也是可行的。

using System;
                    
public class Program
{
    public static void Main()
    {
        var t = GetTheThing("");
        
        if (t == null)
        {
            throw new Exception("Thing could not be made from this arg");
        }
        else
        {
            t.DoSomething();
        }
    }
    
    private static Thing? GetTheThing(string s)
    {
        if (s == "")
        {
            return new Thing();
        }
        else
        {
            return null;
        }
    }
}

public class Thing
{
    public void DoSomething () { Console.WriteLine("Hello, world!"); }
}

工作小提琴在这里

© www.soinside.com 2019 - 2024. All rights reserved.