C# 输出具有可为空引用类型的参数

C# 输出具有可为空引用类型的参数,c#,c#-8.0,nullable-reference-types,C#,C# 8.0,Nullable Reference Types,我为我的一些项目实现了一个选项类型,如下所示: public abstract Option<T> {} public class None<T> : Option<T> public class Some<T> : Option<T> { public T Value { get; } public Some(T value) { Value = value; } } 是否有其

我为我的一些项目实现了一个
选项
类型,如下所示:

public abstract Option<T> {}

public class None<T> : Option<T>

public class Some<T> : Option<T> 
{
    public T Value { get; }

    public Some(T value)
    {
        Value = value;
    }
}
是否有其他方法适用于此问题?我缺少什么?

使用或。我建议使用
MaybeNullWhen
,因为它甚至可以在不受结构或引用类型约束的类型参数上工作

public static bool TryGetValue(此选项,[MaybeNullWhen(false)]输出T值)
{
如果(选项是一些)
{
价值=一些价值;
返回true;
}
值=默认值;
返回false;
}
用法:

if(option.TryGetValue(out var值))
{
value.SomeMethod();//无警告-此处已知值为非null
}
value.SomeMethod();//警告-此处的值可能为空。
该属性在.Net standard 2.1/.new core 3.0之前不可用,但如果不可用,可以自己手动定义。确保它是内部的,否则如果另一个库也将其定义为公共的,并且有人从这两个库继承,则会导致冲突:

名称空间System.Diagnostics.CodeAnalysis
{
///指定当方法返回时,即使相应的类型不允许该参数,该参数也可以为null。
[AttributeUsage(AttributeTargets.Parameter,继承=false)]
内部密封类MaybeNullWhenAttribute:属性
{
///使用指定的返回值条件初始化属性。
/// 
///返回值条件。如果方法返回此值,则关联的参数可能为null。
/// 
public MaybeNullWhenAttribute(bool returnValue)=>returnValue=returnValue;
///获取返回值条件。
公共布尔返回值{get;}
}

(摘自)

到目前为止,使用C#8.0还没有一个完全通用的解决方案

[NotNullWhen()]
属性向前迈出了一步,但接下来我们将遇到以下问题:

一个可空类型参数必须是一个值类型或非可空引用类型。考虑添加一个“类”、“结构”或类型约束。 我想说,这是现在使用nullables的一个主要难点。我希望它能在8.1或其他版本中得到解决

相关讨论——允许泛型方法在不限制类或结构的情况下指定T

作为一种解决方法,可以使用所需的
复制多个扩展方法,其中可以设置
约束,以覆盖所有可能的类型

由于问题已经解决,现在可以在一个扩展类中包含所有重载。但是它仍然需要为每个独立的泛型输出参数增加两倍的扩展方法。Yikes

通过快速查看,我找不到特定于out参数的开放问题。如果还没有完成,可能值得将此特定用例引入csharplang github问题


更新:我在上面提到的问题上做了一个简单的解释。

我想你应该看看Mark Seemann谈论monad。在这之后,你就不再试图从monad中获取值了。:)不管怎样,我想知道不可为null的引用类型的默认值是什么。我复制了你的代码,它不会提示你的警告。Sorry我帮不了你。你使用VS2019吗?为什么不在抽象类上添加一个抽象的
属性,如果
则通过返回默认值来实现它,在
部分
则通过返回它的值来实现它?跟踪问题:
public static bool TryGetValue<T>(this Option<T> option, out T value)
{
    if (option is Some<T> some)
    {
        value = some.Value;
        return true;
    }

    value = default;
    return false;
}
public static bool TryGetValue<T>(this Option<T> option, out T value) 
    where T : nullable [...]