c#可选的Out参数

本文关键字:Out 参数 | 更新日期: 2023-09-27 18:04:26

是否有办法使方法的输出参数可选?我有一个方法,它需要几个参数,大多数时候返回null,但有时它们会有一个值。我试图找出是否有更好的方法来实现这一点,而不是先将值设置为空,或者在if/else之后将它们设置为空。这可能是唯一的方法,但如果有可选的out参数或类似的东西就好了。下面是代码:

    private static void GetInitInfo(string initLine, string ncPointType, out double? relinquishDefault, out bool? ignoreRelinquishDefault, out bool? closedForStart, out bool? adjustDisabled)
    {
        relinquishDefault = null;
        ignoreRelinquishDefault = null;
        closedForStart = null;
        adjustDisabled = null;
        switch (ncPointType)
        {
            case "MSD":
                adjustDisabled = LastToken<bool?>(initLine);
                break;
            case "BO":
                relinquishDefault = SecondToken<double>(initLine);
                closedForStart = ThirdToken<bool?>(initLine);
                ignoreRelinquishDefault = !ForthToken<bool?>(initLine);//ignoreRelDef would be reverse of use initial value
                break;
            case "MSO":
                closedForStart = SecondToken<bool?>(initLine);
                relinquishDefault = ThirdToken<double>(initLine);
                ignoreRelinquishDefault = !ForthToken<bool?>(initLine);//ignoreRelDef would be reverse of use initial value
                break;
            case "AD":
                relinquishDefault = ThirdToken<double>(initLine);
                ignoreRelinquishDefault = false;
                break;
            case "BD":
                relinquishDefault = SecondToken<double>(initLine);
                adjustDisabled = LastToken<bool?>(initLine);
                ignoreRelinquishDefault = false;
                break;
            case "AOS":
                relinquishDefault = FirstToken<double>(initLine);
                ignoreRelinquishDefault = !ThirdToken<bool?>(initLine);//ignoreRelDef would be reverse of use initial value
                break;
        }
    }

c#可选的Out参数

我相信这个问题是在询问必须在方法中分配值与我们的参数,以及是否有任何方法可以规避,即通过保留未分配的值而不是显式地分配它们null

。你一定要写:

public bool OutMethod(out int? output)
{
    output = null;
    return true;
}

或者有一种方法可以这样做:

public bool OutMethod(out int? output)
{
    return true;
}

结果相同吗?

简短的回答是不,这是不可避免的。请参阅文档中的一个示例,该示例包括显式地分配null,并声明:

注意第三个参数被赋值为null。这允许方法可选地返回值。

在。net框架中也可以找到这样的例子。例:Dictionary<TKey,TValue>TryGetValue法:
public bool TryGetValue(TKey key, out TValue value)
{
    int num = this.FindEntry(key);
    if (num >= 0)
    {
        value = this.entries[num].value;
        return true;
    }
    value = default(TValue);
    return false;
}
注意default(TValue)
的显式赋值

根据c# 4.0规范:第21.1节,这是不允许的。

一种解决方法是使用另一个没有out或ref参数的方法进行重载。

使用没有out参数的重载签名:

private static void GetInitInfo(string initLine, string ncPointType)
{
  double? relinquishDefault;
  bool? ignoreRelinquishDefault;
  bool? closedForStart;
  bool? adjustDisabled;
  GetInitInfo( initLine, ncPointType, out relinquishDefault, out ignoreRelinquishDefault, 
    out closedForStart, out adjustDisabled);
}

解释很简单:您可以做到。只需在方法内部将out参数指定为所需的值。

现在你可以问自己,为什么我们不能在方法签名中这样做?好吧,让我们看一下普通的可选值参数。如果调用方没有为它们赋值,则为它们赋一个预定义的值。因此,调用者知道该值,如果参数没有显式设置,则将传递该值。它对它有控制权,它对这个决定负责。

由于方法的调用者不负责out形参的赋值,因此提供默认值没有意义。通过使用默认的out参数值,您唯一可以实现的是让调用者知道该out参数的一个可能值是什么。但这有意义吗?什么时候使用这个值?在什么情况下?这一切对打电话的人来说仍然是隐藏的。因此,除了可以在签名中而不是在方法体中设置外,使用可选的out参数值并没有真正的好处。

所以,话虽如此,下面的内容就没有多大意义了:

public bool TrySomething(out string outObject = "default value") { ... }

然而,允许以下方法

将会很酷
public bool TrySomething(out string outObject) { ... }

按如下方式调用:

bool result = TrySomething();

在后台相当于:

string dummyWhichWillNeverBeUsed;
bool succeeded = TrySomething(out dummyWhichWillNeverBeUsed);

很遗憾,这是不允许的。

当然,正如在其他答案中解释的那样,您总是可以在没有out参数的情况下重载